C++矢量复制赋值,调用其元素的哪种复制机制?
C++ vector copy assignment, calling which copy mechanism of its elements?
我的 class A
显式实现了它的复制构造函数和复制赋值。
复制分配此类元素的向量时使用哪种复制机制?
这是:
vector<A> a1, a2(5);
a1 = a2;
要对 a1
的所有新元素使用 A
的复制构造函数,并将 a2
的元素作为输入?
还是要在 a1
中为元素腾出空间,然后使用 A
的 operator=
和 a2
的元素作为输入?
如果 a1
在赋值前不为空怎么办?
有指定吗?
我的 class 的复制构造函数和 operator=
不完全做同样的事情(这是不好的做法吗?目前主要是测试内容)。看起来复制构造函数被调用了,但我想知道它是否保证是那样的,或者在这种情况下是否恰好是这样。
在此上下文中,它将调用复制构造函数 5 次。由于 a1
为空,因此没有任何元素可以 分配 给。所以他们需要复制构造。
一般来说,它会调用任何copy/move construction/assignment 的混合或删除是适当的。一切都取决于相关向量的大小、您正在执行的特定向量运算以及操作数的值类别。
It looks like the copy constructor is called, but I wonder if it is guaranteed to be that way or if it just happens to be so in this very case.
可以保证基于异常安全swap
的赋值实现:
struct SomeClass
{
SomeClass(const SomeClass& other) { ... }
SomeClass(SomeClass&& other) { ... }
// Copy/move construction is performed while initializing the parameter
void operator=(SomeClass other)
{
this->swap(other);
}
void swap(SomeClass& other) { ... }
};
这种赋值实现的缺点是——由于它的通用性——它不是最优的(例如,在自我赋值的情况下它做了不必要的工作)。
一般来说,如果可以排除异常安全问题,则复制分配给对象可以比销毁它并构建源对象的就地副本更快。因此,您应该期望追求性能的实现会尽可能通过赋值而不是复制构造它们的子对象来执行对象赋值。
我的 class A
显式实现了它的复制构造函数和复制赋值。
复制分配此类元素的向量时使用哪种复制机制?
这是:
vector<A> a1, a2(5);
a1 = a2;
要对 a1
的所有新元素使用 A
的复制构造函数,并将 a2
的元素作为输入?
还是要在 a1
中为元素腾出空间,然后使用 A
的 operator=
和 a2
的元素作为输入?
如果 a1
在赋值前不为空怎么办?
有指定吗?
我的 class 的复制构造函数和 operator=
不完全做同样的事情(这是不好的做法吗?目前主要是测试内容)。看起来复制构造函数被调用了,但我想知道它是否保证是那样的,或者在这种情况下是否恰好是这样。
在此上下文中,它将调用复制构造函数 5 次。由于 a1
为空,因此没有任何元素可以 分配 给。所以他们需要复制构造。
一般来说,它会调用任何copy/move construction/assignment 的混合或删除是适当的。一切都取决于相关向量的大小、您正在执行的特定向量运算以及操作数的值类别。
It looks like the copy constructor is called, but I wonder if it is guaranteed to be that way or if it just happens to be so in this very case.
可以保证基于异常安全swap
的赋值实现:
struct SomeClass
{
SomeClass(const SomeClass& other) { ... }
SomeClass(SomeClass&& other) { ... }
// Copy/move construction is performed while initializing the parameter
void operator=(SomeClass other)
{
this->swap(other);
}
void swap(SomeClass& other) { ... }
};
这种赋值实现的缺点是——由于它的通用性——它不是最优的(例如,在自我赋值的情况下它做了不必要的工作)。
一般来说,如果可以排除异常安全问题,则复制分配给对象可以比销毁它并构建源对象的就地副本更快。因此,您应该期望追求性能的实现会尽可能通过赋值而不是复制构造它们的子对象来执行对象赋值。