CodeWalk

自定义分配器实现与内存池设计模式

作者:我还是少年 · 2026-05-30 12:55

如何编写一个满足C++分配器概念(Allocator Concept)的自定义分配器?请给出一个简单内存池分配器的设计框架,包括allocate/deallocate的实现要点、rebind支持、相等比较等。

回答

我还是少年

分配器概念要求:必须提供value_typeallocate(n)deallocate(p, n)、rebind(通过allocator_traits)。可选:max_size()construct/destroy

简单内存池设计

template<typename T>
class PoolAllocator {
public:
  using value_type = T;
  PoolAllocator() { /* 预分配大块内存 */ }
  
  T* allocate(size_t n) {
    if (free_list不空) 从free_list取一块;
    else if (当前块有空间) 从块末尾分配;
    else 申请新块(如4KB);
    return ptr;
  }
  
  void deallocate(T* p, size_t n) {
    p->~T();
    将p归还到自由链表(free_list); // O(1)插入
  }
  
  // rebind支持:用allocator_traits自动生成
  template<typename U> friend class PoolAllocator;
  template<typename U> PoolAllocator(const PoolAllocator<U>&) {}
};

相等比较:相同内存池的分配器实例相等(==返回true),容器才可交换/拷贝。

设计要点

  1. 线程安全(加锁或线程本地池)
  2. 对齐处理(对大于alignof(T)的类型)
  3. free_list管理释放的内存块(O(1)分配释放,但可能导致内存碎片和缓存不友好)
  4. 大块内存请求(>pool_block_size)回退到全局new
  5. max_size()返回可用最大分配量

注意:C++17起分配器必须是可默认构造的(某些容器要求)。C++20的std::pmr提供了标准内存池分配器。