copy-assignment operator

copy-assignment operator(拷贝赋值运算符):作用于已初始化对象
CP444

1.定义拷贝赋值运算符时也同时需要定义拷贝控制函数,反之亦然。当需CP448需要析构函数时说明也需要拷贝构造函数或者拷贝赋值函数。CP447
2.由于赋值给const是不合法的,赋值给引用不是用户期望的。所以有const和引用成员的类的copy-assignment operator被定义为删除的。CP451,E05

类名& operator=(const 类名&);//类内声明

3.E11处理自我赋值的情况:
首先估计发生自我赋值的概率。如果概率比较高,加入证同测试。
如果有指针成员,在动态分配内存的过程中需要确保程序的异常安全性。

类名& 
类名::operator=(const 类名 &A)//类外定义
{
    if(this==&A) return *this;//证同测试
    auto p1=p;//在new之前先保存1份副本
    p=new (指针指向的对象类型)(*(A.pa));
    delect p1;
    B::operator=(A);//记得复制基类成员
    成员=A.成员;
    …
    return *this;//返回指向左侧运算对象(不是A)的引用
}
//copy and swap

4 E12复制对象的全部部分
对于copy函数(copy constructor和 copy-assignment operator),需要确保复制对象的所有成员变量及基类成分。
如果copy constructor和copy-assignment operator的代码相似,将共同部分放入命名为init的private函数共同调用。

move constructor(移动构造函数)
move-assignment operator(移动赋值函数)
destruct(析构函数)CP445

~类名();//没有返回值,不接受参数

1.首先执行函数体,然后按成员初始化的逆序销毁
2.析构部分是隐式的
3.指向对象的引用或指针离开作用域时,不会执行析构函数(指针被delete后执行)
4.当类需要一个析构函数时,它也需要 copy constructor和copy-assignment operator(为了防止指针成员被拷贝后,导致指针被多次delete)CP447

swap函数:CP458 E25

  • 当类的成员变得复杂时,直接交换2个对象将耗费大量的时间,变成交换指向2个对象的指针速度更快。
  • 对于资源管理类更为重要
class A{
   friend void swap(A&,A&);//为了访问类内的成员
   …
};
inline//考虑到swap函数的作用是为了优化代码,所以将其声明为inline函数。
void swap(A &a1,A &a2)
{
    using std::swap;//不调用标准库的std::swap
    swap(a1.p,a2.p);
    //交换指针,注意此处调用的是为该类成员自定义的swap版本
    …
}

在定义成员版的swap函数后,在类外定义特化版本的swap函数来调用成员版的swap函数。
由于不能改变std命名空间的内容,但是可以为标准模板制造特化版本。

namespace std{
   template<>
   //表明是std::swap的全特化版本,为原模板的所有参数提供实参
   //<A>表示该版本针对类型A设计,一般的函数模板没有<A>
   void swap<A>(A &a1,
               A &a2)
   {
        swap(a1,a2);
   }
}

如果A为类模板时,在类外定义专属版本的swap函数来调用成员版的swap函数。(A为类时也可使用,但是如果要在更大的范围内使用还是使用特化版本)

namespace AStuff{
  …
  template<typename T>
  class A{…};//依然包含成员模板swaptemplate<typename T>
  void swap(A &a1,
             A &a2)
  {
      swap(a1,a2);
  }
} 

编译器在遇到对swap的调用时,首先查找专属版本的swap;没有则查找特化版本的swap;最后再查找一般化的std::swap。CP626,CP615

  • 使用copy and swap定义赋值运算符

由于对内置类型的操作才能够带来高效率,而对对内置类型的操作不会抛出异常。所以成员版的swap不能抛出异常,E29

A& A::operator=(A a)
{
   swap(*this,a);
   //将a中的指针与*this的指针互换
   return *this;
}

在离开该函数后a被自动销毁。自动处理自我赋值并保证异常安全。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值