map/unordered_map 具有不可移动、默认可构造值类型

Rya*_*ing 4 c++ stl move c++11

更新:它出现在23.5.4.3这里版本m[1]应该是有效的

\n\n

更新2m[1]正在使用 gcc4.9.1

\n\n

具体来说,std::mutex。假设我想要一个std::unordered_map<int, std::mutex>. 这可能吗?

\n\n

我似乎无法在不触发已删除的复制构造函数(无论是实习生还是实习生)的某个级别上发生错误的情况下添加 amutexmapmutexstd::pair持有互斥锁的实习生。

\n\n
m.emplace(1);\nm.emplace(1, {});\nm[1];\n
Run Code Online (Sandbox Code Playgroud)\n\n

全部编译失败。我真正想要的只是mutex在内部就地构建map.

\n\n

我宁愿不使用std::unique_ptr<std::mutex>,但我知道这可能是我最好的选择。

\n\n

补充:一个完整​​的例子operator[]添加:在 gcc 和 clang 下对我来说失败的

\n\n
#include <unordered_map>\n#include <mutex>\n\nint main() {\n    std::unordered_map<int, std::mutex> m;\n    m[1];\n\n    return 0;\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

clang3.5 中错误最相关的部分

\n\n
/usr/bin/../lib/gcc/x86_64-linux-gnu/4.7/../../../../include/c++/4.7/bits/stl_pair.h:126:35: error: call to deleted constructor of \'std::mutex\'\n        : first(std::forward<_U1>(__x)), second(__y) { }\n                                         ^      ~~~\n...\n\nf.cpp:6:6: note: in instantiation of member function \'std::__detail::_Map_base<...>::operator[]\' requested here\n    m[1];\n     ^\n/usr/bin/../lib/gcc/x86_64-linux-gnu/4.7/../../../../include/c++/4.7/mutex:163:5: note: \'mutex\' has been explicitly marked deleted here\n    mutex(const mutex&) = delete;\n    ^\n
Run Code Online (Sandbox Code Playgroud)\n\n

和从海湾合作委员会4.7.2

\n\n
In file included from /usr/include/c++/4.7/utility:72:0,\n                 from /usr/include/c++/4.7/unordered_map:38,\n                 from f.cpp:1:\n/usr/include/c++/4.7/bits/stl_pair.h: In instantiation of \xe2\x80\x98constexpr std::pair<_T1, _T2>::pair(_U1&&, const _T2&) [with _U1 = int; <template-parameter-2-2> = void; _T1 = int; _T2 = std::mutex]\xe2\x80\x99:\n/usr/include/c++/4.7/bits/stl_pair.h:273:72:   required from \xe2\x80\x98constexpr std::pair<typename std::__decay_and_strip<_T1>::__type, typename std::__decay_and_strip<_T2>::__type> std::make_pair(_T1&&, _T2&&) [with _T1 = int; _T2 = std::mutex; typename std::__decay_and_strip<_T2>::__type = std::mutex; typename std::__decay_and_strip<_T1>::__type = int]\xe2\x80\x99\n/usr/include/c++/4.7/bits/hashtable_policy.h:463:24:   required from \xe2\x80\x98std::__detail::_Map_base<_Key, _Pair, std::_Select1st<_Pair>, true, _Hashtable>::mapped_type& std::__detail::_Map_base<_Key, _Pair, std::_Select1st<_Pair>, true, _Hashtable>::operator[](_Key&&) [with _Key = int; _Pair = std::pair<const int, std::mutex>; _Hashtable = std::_Hashtable<int, std::pair<const int, std::mutex>, std::allocator<std::pair<const int, std::mutex> >, std::_Select1st<std::pair<const int, std::mutex> >, std::equal_to<int>, std::hash<int>, std::__detail::_Mod_range_hashing, std::__detail::_Default_ranged_hash, std::__detail::_Prime_rehash_policy, false, false, true>; std::__detail::_Map_base<_Key, _Pair, std::_Select1st<_Pair>, true, _Hashtable>::mapped_type = std::mutex]\xe2\x80\x99\nf.cpp:6:8:   required from here\n/usr/include/c++/4.7/bits/stl_pair.h:126:45: error: use of deleted function \xe2\x80\x98std::mutex::mutex(const std::mutex&)\xe2\x80\x99\nIn file included from f.cpp:2:0:\n/usr/include/c++/4.7/mutex:163:5: error: declared here\nIn file included from /usr/include/c++/4.7/utility:72:0,\n                 from /usr/include/c++/4.7/unordered_map:38,\n                 from f.cpp:1:\n/usr/include/c++/4.7/bits/stl_pair.h: In instantiation of \xe2\x80\x98constexpr std::pair<typename std::__decay_and_strip<_T1>::__type, typename std::__decay_and_strip<_T2>::__type> std::make_pair(_T1&&, _T2&&) [with _T1 = int; _T2 = std::mutex; typename std::__decay_and_strip<_T2>::__type = std::mutex; typename std::__decay_and_strip<_T1>::__type = int]\xe2\x80\x99:\n/usr/include/c++/4.7/bits/hashtable_policy.h:463:24:   required from \xe2\x80\x98std::__detail::_Map_base<_Key, _Pair, std::_Select1st<_Pair>, true, _Hashtable>::mapped_type& std::__detail::_Map_base<_Key, _Pair, std::_Select1st<_Pair>, true, _Hashtable>::operator[](_Key&&) [with _Key = int; _Pair = std::pair<const int, std::mutex>; _Hashtable = std::_Hashtable<int, std::pair<const int, std::mutex>, std::allocator<std::pair<const int, std::mutex> >, std::_Select1st<std::pair<const int, std::mutex> >, std::equal_to<int>, std::hash<int>, std::__detail::_Mod_range_hashing, std::__detail::_Default_ranged_hash, std::__detail::_Prime_rehash_policy, false, false, true>; std::__detail::_Map_base<_Key, _Pair, std::_Select1st<_Pair>, true, _Hashtable>::mapped_type = std::mutex]\xe2\x80\x99\nf.cpp:6:8:   required from here\n/usr/include/c++/4.7/bits/stl_pair.h:273:72: error: use of deleted function \xe2\x80\x98constexpr std::pair<_T1, _T2>::pair(std::pair<_T1, _T2>&&) [with _T1 = int; _T2 = std::mutex; std::pair<_T1, _T2> = std::pair<int, std::mutex>]\xe2\x80\x99\n/usr/include/c++/4.7/bits/stl_pair.h:120:17: note: \xe2\x80\x98constexpr std::pair<_T1, _T2>::pair(std::pair<_T1, _T2>&&) [with _T1 = int; _T2 = std::mutex; std::pair<_T1, _T2> = std::pair<int, std::mutex>]\xe2\x80\x99 is implicitly deleted because the default definition would be ill-formed:\n/usr/include/c++/4.7/bits/stl_pair.h:120:17: error: use of deleted function \xe2\x80\x98std::mutex::mutex(const std::mutex&)\xe2\x80\x99\nIn file included from f.cpp:2:0:\n/usr/include/c++/4.7/mutex:163:5: error: declared here\n
Run Code Online (Sandbox Code Playgroud)\n

Seb*_*edl 5

两个选择。

一是你尝试的第三件事,m[1]应该编译。你遇到了什么错误?

第二种是emplacepiecewise_construct构造函数一起使用:

m.emplace(std::piecewise_construct, std::make_tuple(1), std::tuple<>());
Run Code Online (Sandbox Code Playgroud)

应该可以工作,尽管我认为很可能存在标准库而没有。

  • “除非我们强制 unordered_map 将每个元素存储在它自己的节点中” - 这正是我们正在做的。23.2.5/8 说:“重新散列会使迭代器无效,更改元素之间的顺序,并更改元素出现在哪些存储桶中,但不会使元素的指针或引用无效。” 不使引用无效的唯一方法是将每个元素保留在其自己的节点中并且仅操作指针。进一步注意,这些要求仅要求用于非常特定功能的元素可移动/可复制,而不是所有插入功能(如果重新散列可以移动它们)。 (2认同)