Construct unordered_map with a value_type of unique_ptr

Construct unordered_map with a value_type of unique_ptr

本文关键字:type of unique value ptr unordered map with Construct      更新时间:2023-10-16

这段代码似乎不起作用,因为唯一指针被存储到一个对对象中,然后试图从中复制。这能避免吗?

std::unordered_map<std::string,std::unique_ptr<int>> _map {
{"hello", std::make_unique<int>(7)}
};

完整的代码示例和编译错误可以在这里看到 http://cpp.sh/7uc3a

是的,不使用列表初始化。

std::unordered_map<std::string,std::unique_ptr<int>> _map;
_map.insert({"hello", std::make_unique<int>(7)});

std::unordered_map需要调用复制或移动构造函数,以便将任何键和值存储在其内部缓冲区中。在std::unique_ptr的情况下,复制构造函数被删除,因为复制std::unique_ptr会使它根本不是唯一的。这只剩下移动构造函数。 问题在于初始化地图的方式:

std::unordered_map<std::string,std::unique_ptr<int>> _map {
{"hello", std::make_unique<int>(7)}
};

您正在使用std::initializer_list初始化地图的值。

从 cpp 首选项:

std::initializer_list 类型的对象是一个轻量级代理对象,提供对const T类型的对象数组的访问。

实际上,初始值设定项列表中的所有值都是常量值。这意味着无法调用std::unique_ptr上的移动构造函数,因为移动对象通常需要修改原始实例。由于无法移动std::unique_ptr,编译器会回退到复制构造函数,这就是为什么它最终会抱怨复制构造函数被删除的原因。

我发布的代码段之所以有效,是因为insert接受一个非常量std::pair,这意味着std::unique_ptr是非常量,并且可以调用其移动构造函数。

相关文章: