• 条款11:在operator=处理自我赋值


    自我赋值发生在对象被赋值给自己:

    class Widget {

    ...

    }

    Widget w ;

    w = w // 赋值给自己

    还有一个隐含的会发生自我赋值的例子:

             a[i]  = a[j];//当i = j时

    下面有这样一个类:

    class Bitmap{};

    class Widget {

           ...

    private :

           Bitmap *pb;

    };

    l  版本一

    Widget& Widget::operator= (const Widget& rhs){

                  delete pb;

                  pb = new Bitmap(*rhs.pb);

                  return *this;

    }

    注意:这里存在一个问题,那就是如果rhs所指的对象就是this。Delete pb后,就把this的pb删除了,所以不行。

    欲阻止这样的错误,可以加上一个证同测试:

    l  版本二

    Widget& Widget::operator= (const Widget& rhs){

                  if(this == rhs) return *this; // 证同测试

                  delete pb;

                  pb  = new Bitmap(*rhs.pb);

                  return *this;

    }

    这样做法是可以的,但是还有一个问题是如果在new Bitmap时,出现的异常,则会使widget对象最终会持有一个指针指向一块被删除的bitmap。这样的指针是有害的,你无法安全的删除它们,也无法安全的读取它们。

    但是精心安排一下,是可以避免这个错误的:

    l  版本三:

    Widget& Widget::operator= (const Widget& rhs){

                  Bitmap *obj = rhs.pb;

                  pb  = new Bitmap(*rhs.pb);

                  delete obj;

                  return *this;

    }

    现在如果new Bitmap出现的异常,pb也会保持原状。注意,虽然我们没有加入证同测试,但是上面的代码也可以处理自我赋值现象。

    版本四:

    针对版本三还有一个替换版本:

    class Widget {

    public:

        ...

        swap(Widget& rhs);

    private :

        Bitmap *pb;

    };

    Widget& Widget::operator= (const Widget& rhs){

               Widget temp(rhs);

               swap(temp);

               return *this;

    }

    这项技术被称为copy and swap技术。

    • 请记住:
    • 确保当对象自我赋值时operator=有良好的行为。其中的技术包括
    1. 比较“来源对象”与“目标对象”的地址
    2. 精心周到的语句顺序
    3. Copy and swap技术
    • 确定任何函数如果操作一个以上的对象,而其中多个对象是同一个对象时,其行为也是正确的
  • 相关阅读:
    poj1068
    make&&gcc/g++ 生成 map file
    游戏系统开发笔记(九)——构建战斗系统
    归并排序
    士兵杀敌(四)
    ftp报错 200 port command successful. consider using pasv 425 failed to establish connection
    HDU 4649 Professor Tian
    如何将ASM中的数据文件复制到操作系统中
    Struts2 学习笔记 10 Result部分 part1
    交通管理系统
  • 原文地址:https://www.cnblogs.com/loveyakamoz/p/2772384.html
Copyright © 2020-2023  润新知