cppreference的精选语录:
这种运行时多态性使得使用polymorphic_allocator的对象表现出在静态分配器类型相同的情况下,就好像它们在运行时使用了不同的分配器类型
“常规”分配器的问题在于它们会改变容器的类型。如果您想要一个具有特定分配器的vector,则可以利用Allocator模板参数:
auto my_vector = std::vector<int,my_allocator>();
现在的问题是这个向量类型与使用不同分配器的向量类型不同。例如,您无法将其传递给需要默认分配器向量的函数,或将具有不同分配器类型的两个向量赋值给相同的变量/指针,如下所示:
auto my_vector = std::vector<int,my_allocator>();
auto my_vector2 = std::vector<int,other_allocator>();
auto vec = my_vector; // ok
vec = my_vector2; // error
多态分配器是一种单一的分配器类型,其成员可以通过动态分派而不是模板机制来定义分配器行为。这使您可以拥有使用特定自定义分配的容器,但仍属于通用类型。
通过给分配器传递std::memory_resource *
来自定义分配器行为:
// define allocation behaviour via a custom "memory_resource"
class my_memory_resource : public std::pmr::memory_resource { ... };
my_memory_resource mem_res;
auto my_vector = std::pmr::vector<int>(0, &mem_res);
// define a second memory resource
class other_memory_resource : public std::pmr::memory_resource { ... };
other_memory_resource mem_res_other;
auto my_other_vector = std::pmr::vector<int>(0, &mes_res_other);
auto vec = my_vector; // type is std::pmr::vector<int>
vec = my_other_vector; // this is ok -
// my_vector and my_other_vector have same type
据我看,目前主要的问题是std::pmr::
容器仍然与使用默认分配器的等效std::
容器不兼容。在设计与容器一起工作的接口时,您需要做出一些决策:
- 传入的容器可能需要自定义分配,这是很可能的吗?
- 如果是这样,我应该添加一个模板参数(允许任意分配器)还是应该强制使用多态分配器?
模板解决方案允许使用任何分配器,包括多态分配器,但具有其他缺点(生成的代码大小、编译时间、必须在头文件中公开代码、潜在的进一步“类型污染”将问题推向外部)。另一方面,多态分配器解决方案指定必须使用多态分配器。这排除了使用使用默认分配器的std::
容器,并可能对与旧代码的接口产生影响。
与常规分配器相比,多态分配器确实具有一些小成本,例如内存资源指针的存储开销(最可能是可以忽略不计的),以及为分配而进行虚函数调度的成本。真正的主要问题可能是与不使用多态分配器的旧代码的兼容性不足。
allocator<T>
固有的一些问题。 - edmz