将try_emplace与shared_ptr一起使用

Riv*_*Tam 2 c++

所以我有一个std::unordered_map<std::string, std::shared_ptr<T>>,我想try_emplace用来添加/引用元素.以前,它只是一个std::unordered_map<std::string, T>并且T有一个构造函数只需要一个std::string,所以我用它myMap.try_emplace(myString, myString).first->second来引用T并在必要时创建它.

但是,如果我只是将其更改为myMap.try_emplace(myString, std::make_shared<T>(myString)).first->second,它当然会T每次构建它.

什么是解决这个问题最惯用的方式?为了澄清,我想使用共享指针在堆上构造对象,并且当且仅当映射中不存在匹配元素时,才将共享指针插入到无序映射中.

Sla*_*ica 6

你可以operator[]改用:

auto &ptr = map[ key ];
if( !ptr ) ptr = std::make_shared<T>( myString );
Run Code Online (Sandbox Code Playgroud)

注意:此解决方案假设您不希望std::shared_ptr在地图中保留默认构造.如果是这种情况,那么您需要使用更详细的代码try_emplace:

auto p = map.try_emplace( key, nullptr );
if( p.second ) p.first->second = std::make_shared<T>( myString );
else {
    if( !p.first->second ) { // handle nullptr }
}
auto &ptr = p.first->second;
Run Code Online (Sandbox Code Playgroud)

  • @MaxLanghof我们不构造`T`你正在构造`shared_ptr <T>`,它总是有一个默认的构造函数. (4认同)