一个类必须拥有拷贝构造、移动构造、拷贝赋值、移动赋值、析构函数。如果它们未被显式定义,编译器将会自动合成它们。
默认的拷贝构造函数会将源对象的成员依次复制到新对象中,如果成员中有类类型,还会调用它们的拷贝构造函数。
拷贝初始化通常调用拷贝构造函数完成,有时也会调用移动构造函数。拷贝初始化不仅在我们定义类对象时发生,也会在传递非引用参数、返回非引用对象、初始化列表时发生。
拷贝构造函数的参数必须为引用类型。如果不是引用类型,当构造发生时,形参必须拷贝实参,由此调用拷贝构造函数,为了调用拷贝构造函数,又必须拷贝实参……
explicit关键字,防止自动类型转换。
class Class{
public:
c(int arg);
c(int a, intb);
private:
int a;
};
当我们Class c = 1或者Class c = { 1, 2 } 时,编译器会调用构造函数将等号后面的内容自动转换Class类型。使用explicit可以防止这种行为。
在一个构造函数中,成员的初始化是在函数体之前完成的,而析构函数相反,成员的销毁在函数体之后,按初始化顺序的逆序完成。隐式销毁一个内置指针类型不会delete其所指的对象。
什么时候会调用析构函数:
无论何时一一个对象被销毁,就会自动调用其析构函数:
● 变量在离开其作用域时被销毁。
● 当一个对象被销毁时,其成员被销毁。
● 容器(无论是标准库容器还是数组)被销毁时,其元素被销毁。
● 对于动态分配的对象,当对指向它的指针应用delete运算符时被销毁。
● 对于临时对象,当创建它的完整表达式结束时被销毁。
如果类成员包含指针,使用合成构造函数时,源对象被简单拷贝至新的对象,包括指针,会导致新对象与源对象成员指针指向同一个目标。
用=default声明使用默认的合成函数,用=delete定义删除的函数。=default可以在声明或者定义使用,不过在类里会被声明为内联。=delete必须出现在函数第一次出现的地方。
不能删除析构函数,析构函数被删除意味着对象无法被销毁。
本质上,当不可能拷贝、复制、销毁类的成员时,类的合成拷贝控制成员就被定义为删除的。
调用类的swap函数,而不是std::swap



