重载的赋值运算符中必须要判断处理自赋值的情景,即自己赋值给自己。
class Bitmap { ... };
class Widget {
...
private:
Bitmap *pb; // ptr to a heap-allocated object
};
Widget&
Widget::operator=(const Widget& rhs) // unsafe impl. of operator=
{
delete pb; // stop using current bitmap
pb = new Bitmap(*rhs.pb); // start using a copy of rhs's bitmap
return *this; // see Item 10
}
上面的重载赋值运算符在自赋值时就会发生异常,第二行是对已释放的指针进行了*操作。
加入自赋值判断进行保护如下:
Widget& Widget::operator=(const Widget& rhs)
{
if (this == &rhs) return *this; // identity test: if a self-assignment,
// do nothing
delete pb;
pb = new Bitmap(*rhs.pb);
return *this;
}
如果在new时发生异常,pb指针指向内容已经释放,为了更安全可以用临时变量暂时保存:
Widget& Widget::operator=(const Widget& rhs)
{
Bitmap *pOrig = pb; // remember original pb
pb = new Bitmap(*rhs.pb); // make pb point to a copy of *pb
delete pOrig; // delete the original pb
return *this;
}
当new完全成功时,再释放掉原来指向的内存区域。
还有提到了 swap and copy 模式,可见条款29.
阅读(239) | 评论(0) | 转发(0) |