以下代码:
std::pmr::vector<std::pmr::vector<int>> outer_vec(std::pmr::get_default_resource());
outer_vec.emplace_back(std::pmr::get_default_resource());
失败,出现难以想象的错误消息,结尾为
静态断言失败:如果 uses_allocator为 true,则必须可以使用分配器进行构造
向量可以用std::pmr::get_default_resource()
参数清楚地构造,例如:
std::pmr::vector<std::pmr::vector<int>> outer_vec(std::pmr::get_default_resource());
std::pmr::vector<int> inner_vec(std::pmr::get_default_resource());
outer_vec.push_back(std::move(inner_vec));
std::pmr::vector
可以使用emplace_back
来构造元素,例如:
std::pmr::vector<std::vector<int>> outer_vec(std::pmr::get_default_resource());
outer_vec.emplace_back();
为什么两者的结合会失败?什么static_assert
失败了?
请注意,如果外部向量不pmr
,则它有效:
std::vector<std::pmr::vector<int>> vec;
vec.emplace_back(std::pmr::get_default_resource());
如果构造类型支持,std::pmr::polymorphic_allocator
使用使用分配器构造。std::vector
确实支持用途分配器构造,并且内std::vector
的分配器类型与外部分配器的类型兼容。
因此,分配器构造将被外部向量使用。这意味着,每当向量构造一个新元素时,它都会自动将其自己的分配器作为另一个参数传递给元素的构造函数。(具体来说,在这种情况下,get_allocator()->resource()
在参数列表的末尾传递。
您正在尝试手动将分配器传递给emplace_back
,因此实际上上述两个分配器将传递给内部向量的构造,从而导致失败。
所以,你真正想要的只是outer_vec.emplace_back();
.它将外部向量的分配器传播到内部向量。
请注意,outer_vec.push_back(std::move(inner_vec));
也会这样做。它还会将外部分配器传播到新的"move"构造的内部向量,从而在必要时将所有元素移动到新的分配中。如果它的分配器与outer_vec
的分配器不相等,则它不会使用原始的inner_vec
分配。