zoukankan      html  css  js  c++  java
  • Effective C++ Item 10,11 Have assignment operators return a reference to *this Handle assignment to self in operator =

    If you want to concatenate assignment like this

    int x, y, z;
    x = y = z = 15;
    

    The convention is to make the assignment operators return a reference to *this.

    11 Handle assignmnet to self in operator = 

    You can easily assign an object to itself without knowing it

    // Example 1
    Foo *px, *py;
    px = py;
    
    //Example 2
    a[i] = a[i];
    

    It is dangerous to assign an object to self if your class doesn't handle this kind of opeator appropriately. Let's consider an example here:

    class Bitmap{...};
    
    class Widget {
    	...
    private:
    	Bitmap *m_pb;
    };
    
    Widget& Widget::operator=(const Widget& rhs) {
    	delete m_pb;
    	m_pb = new Widget(rhs);
    	return *this;
    }
    

    You will be dead if you assign an object to itself, beacause you will end up holding a pointer to a deleted object!

    One way but not the best way to deal with self assignment is to write code to explicitly deal with this situation:

    Widget& Widget::operator=(const Widget& rhs) {
    	if(this == &rhs) {
    		return *this;
    	}
    	
    	delete m_pb;
    	m_pb = new Bitmap(*rhs).m_ph;
    	return *this;
    }
    

    This is not the best way because above this operator is not exception-safe. What does that mean? Imagine what if an exception is thrown when

    ph = new Bitmap(*rhs.m_ph)
    

    is been executed(for example, not enough memory), then the object will hold a pointer to a deleted object.

    Luckily, making operator= safe renders it self-assignmnet-sage, too. So, the best way to accomplish that is:

    Widget& Widget::operator=(const Widget& rhs) {
    	Bitmap* tmp = m_pb;
    	pb = new Bitmap(*rhs.m_pb);
    	delete tmp;
    	return *this;
    }
    

    Now if "new Bitmap" throw an exception, pb remains unchanged. Even without the identity test, this code handle assignment to self, because we make a copy of the original bitmap, point to the copy we made, and then delete the original Bitmap.

    A more straightforward way to do so is to use exception-safe function swap

    Widget& Widget::operator=(const Widget& ths) {
    	Widget temp(ths);
    	swap(temp);
    	return *this;
    }
    

      

  • 相关阅读:
    Spring AOP切点表达式用法总结
    各种文档地址记录
    回顾乐信集团工作经历
    Redux的简单使用
    简单介绍软件测试(一)
    jupyter notebook 安装代码提示功能
    解决matplotlib不显示中文的问题
    前端生成二维码并下载(PC端)
    XSS绕过常见方式
    JWT的安全问题
  • 原文地址:https://www.cnblogs.com/xinsheng/p/3572668.html
Copyright © 2011-2022 走看看