可以 std::set::insert() 调用赋值运算符
Can std::set::insert() call the assignment operator?
我有一个带有自定义赋值运算符的类,它故意引入了受控的副作用。
如果我对这些元素有std::set
,我想知道是否可以使用 insert
调用赋值运算符。
即:
class A
{
public:
A & operator=(A const & rhs)
{
// custom assignment operator with deliberate side effects
// Could this be called with use of std::set::insert()?
}
};
std::set<A> a;
// Is it possible with this, or any use of "insert", that
// the assignment operator will ever be called?
a.insert(A());
是否可以使用 std::set::insert
调用赋值运算符?
在 C++11 之前,理论上可以。 毫无疑问,C++11禁止它因为没有实现真正做到过。 In C++11,std::set
的成员不必支持分配。在 C++11 之前,一些支持概念的实现可能会具有使用赋值的代码,作为检查您的类支持它,但它应该处于未计算的上下文,因此实际上不会调用运算符。
C++11 标准要求与std::set::insert
一起使用的类型是"CopyInsertable"、"移动可插入"或"可放置",具体取决于您使用的插入函数 (23.2.3/4)。
例如,这被定义为:
T 是 EmplaceConstructible from args 到 X,对于零个或多个参数 args,表示以下表达式格式正确:
allocator_traits<A>::construct(m, p, args);
(23.2.1/13)
在所有三种情况下,默认行为都是std::allocator
使用放置 new (17.6.3.5/2):
::new((void*)c)A(forward<Args>(args)...)
根据insert
函数的不同,在我们的例子中,args
要么是 A
类型的表达式,A
类型的右值或其他一些参数。但在所有情况下都使用构造函数或复制构造函数,而不是赋值运算符。
这就是标准所说的(GCC 4.6.3 就是这样)。即使没有理由使用赋值运算符,某些编译器仍可能这样做。所以我建议不要过分依赖它。
相关文章:
- 为用户定义的类正确调用复制构造函数/赋值运算符
- 为什么初始化时没有调用重载赋值运算符?
- 为什么我需要三个嵌套的大括号来调用赋值运算符,将const引用到二维数组
- 使用赋值运算符将宏转换为函数调用
- 从赋值运算符调用构造函数
- 赋值运算符重载在通过指针访问时不调用
- 为什么为单个赋值操作调用复制构造函数和重载赋值运算符
- 在其赋值运算符方法中调用对象的析构函数
- 为什么在没有赋值运算符的情况下调用转换构造函数
- 未调用移动赋值运算符
- 初始化对象后,用隐式转换而不是赋值运算符调用构造函数有什么意义
- C++重载赋值运算符在不相关的类中被调用
- 为什么deque::erase()调用赋值运算符
- C++ 不调用赋值运算符
- 正在数组上调用赋值运算符
- 为什么调用赋值运算符会触发销毁函数
- 为C++中具有多个继承派生类的vtables的基之一调用赋值运算符
- 为什么这里不调用赋值运算符?
- 为什么在这种情况下不调用赋值运算符以支持复制构造函数
- 可以 std::set::insert() 调用赋值运算符