实现operator=时的常用技巧
class Point{
private:
int x;
int y;
public:
Point(const Point& p):x{p.x},
y{p.y}{}
};
class Rectangle{
private:
Point *point;
public:
Rectangle(){
point = nullptr;
}
~Rectangle(){delete point;}
Rectangle(const Rectangle& rect):point(rect.point ? new Point{*rect.point} : nullptr){}
Rectangle& operator=(const Rectangle& rect){
if(this == &rect){
return *this;
}
Rectangle tmp{rect}; // 使用拷贝构造函数进行copy
std::swap(point, tmp.point); // 使用swap进行替换
}
};
使用一个临时变量进行copy然后swap是一个很巧妙的方式,否则就需要大量的判断this->point是否为nullptr, rect.point是否为nullptr做很多处理,但这里最关键的是拷贝构造函数Rectangle(const Rectangle& rect)
要写对;
这里引入了李建忠老师说的三法则,如果定义了析构函数,那是拷贝构造函数和赋值函数都是需要定义的,因为析构一定涉及到非字面字节拷贝的资源的处理,存在这样的资源的时候,使用编译器生成的拷贝构造函数和赋值函数是会有问题的,比如上面的Rectangle->point; 但如果能保证一定不涉及到拷贝赋值操作,那在规范上最好delete处理;
class Rectangle{
private:
Point *point;
public:
Rectangle(){
point = nullptr;
}
~Rectangle(){delete point;}
Rectangle(const Rectangle& rect) = delete; //不使用
Rectangle& operator=(const Rectangle& rect) = delete; //不使用
};