C++实现类的拷贝赋值运算符的注意事项
**当编写赋值运算符是应记住:**将一个对象赋予它自身,赋值运算符应能正确工作!
比如说有这么一个类:
class Test {
public:
Test(const std::string &s = std::string())
: ps(new std::string(s)), i(0) {}
Test(const Test &ori)
: ps(new std::string(*ori.ps)), i(ori.i) {}
~Test();
Test &operator=(const Test &rhs);
private:
std::string *ps;
int i;
};
Test::~Test() {
delete ps;
}
如果你的赋值运算符这么写:
Test &Test::operator=(const Test &rhs) {
delete ps;
ps = new std::string(*rhs.ps);
i = rhs.i;
return *this;
}
那么如果rhs和 *this是同一个对象时,delete会释放掉rhs和 *this指向的string,然后我们要new一个 *rhs.ps时,就会访问一个指向无效内存的指针而导致出错。
正确的做法:
Test &Test::operator=(const Test &rhs) {
auto newps = new std::string(*rhs.ps);
delete ps;
ps = newps;
i = rhs.i;
return *this;
}
应先拷贝右侧运算对象,然后再删除。