c++11 - 对<string,string>的删除赋值运算符的g++编译器错误

标签 c++11 stl

我认为以下简化的 C++11 代码应该是有效的。

unordered_map<string,string> test;
auto it = remove_if( test.begin(), test.end(),
    [] (const decltype(test)::value_type &entry) { return true; } );

但它无法使用 g++ 6.3 编译,提示 std::pair 的赋值运算符已删除,但 AFAIK 未删除该运算符。
/usr/include/c++/6/bits/stl_algo.h:868:16: error: use of deleted function ‘std::pair<_T1, _T2>& std::pair<_T1, _T2>::operator=( ...
*__result = _GLIBCXX_MOVE(*__first);

这是编译器/glibc 错误还是由于某些原因我看不到代码真的无效?

最佳答案

我们来看remove_if文档:

The type of dereferenced ForwardIt must meet the requirements of MoveAssignable.



也就是说,“给定 t ,类型为 T 的可修改左值表达式和 rv ,类型为 T 的右值表达式, 表达式 t = rv必须有效并且[行为如预期]”。

在这里,您通过unordered_map<string, string>的迭代器到 remove_if .我们来看一下。根据 unordered_map documentation ,

value_type is defined as std::pair<const Key, T>



所以,std::pair<const string, string> .

让我们看看对的 operator= .最为显着地:

template< class U1, class U2 > pair& operator=( const pair<U1,U2>& other ); does not participate in overload resolution unless std::is_assignable_v<first_type&, const U1&> and std::is_assignable_v<second_type&, const U2&> are both true.



在这里, std::is_assignable_v<const string&, const string&> 不是真的,因此运算符不可用。因此,该对不是 MoveAssignable。因此 remove_if不能用于那些迭代器。

所以这会使您的代码无效。

关于c++11 - 对<string,string>的删除赋值运算符的g++编译器错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46421095/

相关文章:

c++ - 是否可以使用符合 C++17 的 C++14 创建迭代器?

c++ - std::set(红/黑树)前向迭代是如何实现的?

c++ - g++ 编译错误 : `.rodata' can not be used when making a shared object; recompile with -fPIC

c++ - 自动引用和迭代器

c++ - 带有引用折叠的函数模板重载

c++ - 具有来自 STL 的 vector 、列表或映射作为成员的类是否需要复制构造函数

c++ - 使用 std::min_element() 时保存函数计算

c++ - 如何从重载解析中删除函数?

C++:没有匹配的调用函数:为什么需要一个空的构造函数?

c++ - 如果我们无法从 C++ 容器中删除元素,我们该怎么办