STL自定义分配器来管理不同的内存空间

时间:2009-10-21 23:21:59

标签: c++ stl memory-management

我想使用STL自定义分配器类的不同实例来管理不同的内存空间,然后能够为STL容器指定一个分配器实例,这样每个容器只能从其分配的内存空间中进行绘制。但我不明白我该怎么做。我看到如何将分配器类型传递给STL容器的模板参数,但我想要一些类似于将分配器实例传递到STL容器的构造函数中的东西。有没有办法在STL中这样做?

3 个答案:

答案 0 :(得分:17)

不幸的是,STL分配器不能具有状态(或者至少必须非常小心如何使用该状态) - 特定分配器类型的每个实例必须等效于STL容器才能有效地使用它们。我现在不记得细节,但我知道Scott Meyers在"Effective STL"中详细讨论了这个问题,第10项:注意分配器约定和限制。

但是,可以具有与分配器类型中封装的分配器之间的差异非常相似的模板化分配器,并使用分配器模板的不同“实例化”(每个模板的“实例化”是不同的类型)。再一次,我的回忆是迈耶斯非常清楚地讨论了这个问题。

例如,请参阅Anthony Aue, "Improving Performance with Custom Pool Allocators for STL"的文章中的这一段:

  

一个可能更严重的警告是,由于分配器使用非静态数据,因此技术上不符合标准,因为标准要求相同类型的分配器是等效的。有关问题的详尽说明,请参阅有效STL(第10项)。这相当于要求给定类型的分配器能够释放由该类型的分配器的任何其他实例分配的内存。对于标准容器的许多用途,这个要求是不必要的(有些人可能会说Draconian)。但是,有两种情况需要这个要求:list :: splice和swap()。 swap()的情况特别严重,因为需要以异常安全的方式对容器实现某些操作(参见Exceptional C ++,Item 12)。从技术上讲,交换可能(并且在某些情况下)是面对分配器而实现的,这些分配器不能同等地比较可以复制的项目,或者分配器可以与数据一起交换 - 但情况并非总是如此。因此,如果您使用的是swap()或list :: splice,则应确保使用HoldingPolicySingleton;否则,你一定会遇到一些非常讨厌的行为。

另见Stephan T. Lavavej在this newsgroup thread中的讨论。

如果其他人在此期间没有提供详细信息,我今晚会更新。

答案 1 :(得分:6)

STL容器允许您将分配器作为参数传递给构造函数。

例如,这里是vector的适当构造函数:

explicit vector(const Allocator& = Allocator());
explicit vector(size_type n, const T& value = T(),
  const Allocator& = Allocator());
template <class InputIterator>
vector(InputIterator first, InputIterator last,
  const Allocator& = Allocator());

默认情况下,它们只使用默认的构造分配器。

答案 2 :(得分:0)

也许您可以编写一组分配器类型,其中包含指向单独内存空间的静态。

然后,当STL容器构造其分配器时,分配器使用分配给该分配器的内存空间。

为简单起见,假设您要使用两个内存空间。创建两个分配器类型,每个空间一个。根据需要将分配器类型传递给STL容器构造函数。