同时使用 copy-and-swap idiom在一个具有常量引用作为成员的类中, 出现上述错误。
示例代码:
#include <iostream>
#include <functional>
using std::reference_wrapper;
class I_hold_reference;
void swap(I_hold_reference& first, I_hold_reference& second);
class I_hold_reference{
inline I_hold_reference(const int& number_reference) : my_reference(number_reference){}
friend void swap(I_hold_reference& first, I_hold_reference& second);
inline I_hold_reference& operator=(I_hold_reference other){
swap(*this, other);
return *this;
}
inline I_hold_reference& operator=(I_hold_reference&& other){
swap(*this, other);
return *this;
}
private:
reference_wrapper<const int> my_reference;
};
void swap(I_hold_reference& first, I_hold_reference& second){
first = I_hold_reference(second.my_reference); //error: use of overloaded operator '=' is ambiguous (with operand types 'I_hold_reference' and 'I_hold_reference')
}
当复制赋值运算符被更改为按引用而不是按值获取其参数时,错误已修复。
inline I_hold_reference& operator=(I_hold_reference& other){ ... }
为什么这会修复错误? 一种可能的含义是 Important optimization possibility链接问题中引用的内容丢失了。引用资料是这样吗? 此更改的其他含义是什么?
有一个依赖此运算符的代码库,没有其他成员存在,只有提到的引用。是否需要以某种方式使代码库适应这种变化,或者它是否安全?
最佳答案
如果您仔细按照您链接的描述进行操作,您会发现您必须只有一个 operator=
重载,并且该重载需要按值获取其参数。因此,只需删除 operator=(I_hold_reference&&)
重载即可使您的代码可编译。
然而,这不是唯一的问题。你的 swap
没有交换!相反,它将 second
的拷贝分配给 first
并保持 second
不变。
这就是你想要的:
class I_hold_reference
{
I_hold_reference(const int& number_reference)
: my_reference(number_reference){}
friend void swap(I_hold_reference& first, I_hold_reference& second)
{
using std::swap;
swap(first.my_reference, second.my_reference);
}
I_hold_reference& operator=(I_hold_reference other)
{
swap(*this, other);
return *this;
}
private:
reference_wrapper<const int> my_reference;
};
注意:我删除了不必要的 inline
,因为成员函数是隐式内联的。我还在您的类中声明了 swap
函数。您可以在您共享的链接中找到对此的解释。
此外,在这个特定示例中,首先没有必要使用 copy-and-swap 习惯用法。 std::reference_wrapper
不是手动维护的资源,这意味着它具有适当的内置复制和移动语义。因此,在这个特定示例中,编译器生成的复制和移动运算符将具有与在这里手动创建的。所以,你应该使用那些而不是以任何方式编写你自己的。另一方面,如果这只是一个玩具示例,而实际类中更多资源确实需要手动管理,那么这就是要走的路。
关于c++ - 错误 : ambiguous overload for 'operator=' in swap function using the copy-and-swap idiom,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58690089/