In C + + in operator= processing "self assignment" (one)---"Effective C + +" __c++

Source: Internet
Author: User
clause 11: Handling "self-assignment" in * * Key content **operator=

"Self-assignment" occurs when an object is assigned to itself:
Class widget{...}
Widget W;
w=w;//Assign to yourself
a[i]=a[j];//potential self assignment, if I and J have the same value, this is a self assignment
*px=*py;//potential self assignment, if PX and py point to the same problem, this is also a self assignment
This can even be done as follows:
Class Base {...};
Class Derived:public Base {...};
void dosomething (const base& rb,derived* PD);//rb and PD may actually be the same object

In many cases, "self assignment" is safe without extra fuss, but if you try to manage resources yourself (if you're going to write a class for resource management), you may fall into the trap of "releasing it before you stop using resources", such as:

Class Bitmap {...};
Class widget{...
    bitmap* pb;

widget& widget::operator= (const widget& RHS)
    delete pb;
    Pb=new Bitmap (*RHS.PB);
    return *this;

The problem here is that the internal *this and RHS of the operator= function may be the same object, and if so, the delete PB destroys not only the bitmap of the current object, but also RHS bitmap is destroyed, Then when you assign a value, the program will find that the RHS.PB pointer is pointing to an object that has been deleted.

How to stop this error, there are several ways:
1 The traditional approach is to operator= the front plus a "certificate with the test" to achieve "self assignment" of the calibration purposes, see the following code:

widget& widget::operator= (const widget& RHS) {
    if (THIS==&RHS) return *this;//certificate same test

    delete pb;
    Pb=new Bitmap (*RHS.PB);
    return *this;

Is there anything wrong with this code? You can see that with the "self-assignment security," then what's the problem. The answer is "exceptional security", a workaround that has little effect on the exception, specifically if the new Bitmap (*RHS.PB) has an exception (whether due to an out-of-memory allocation or a Bitmap copy constructor throws an exception), The PB eventually points to a deleted bitmap, and such a pointer can cause a problem such as a null pointer anomaly.
2 This approach focuses mainly on the "exception security" aspect, we only need to pay attention to the assignment PB refers to the things do not remove PB:

widget& widget::operator= (const widget& RHS) {
    bitmap* porig=pb;
    Pb=new Bitmap (*RHS.PB);
    Delete porig;//Remove the original PB return

in this case, if the "new Bitmap" throws an exception, PB remains the same, even if there is no "proof of the same test", this code can still handle the self assignment, because we made a copy of the original Bitmap, delete the original Bitmap, and then point to the newly manufactured copy. PS: If you need to consider efficiency at this point, you need to first estimate how often the "self assignment" occurs. If it's high, we'll add the "proof and test" to the beginning of the function. If the "Proof and test" frequency is not high, it is recommended not to add "proof of the same test", because the addition of this test will cost, reduce program execution efficiency.

3 If the above two methods are still not satisfied, there is an alternative, not only "abnormal security" and "self-assignment security", that is, using the copy and swap technology, see the following code:

Class widget{...
    void swap (widget& rhs);
widget& widget::operator= (const widget& RHS) {
    Widget temp (RHS);//Use the copy constructor to make a copy of the RHS data
    (temp ); Exchanging the *this data and the data of the said complex with the return

How, this method is good. But the code doesn't seem to be as clear as logic, and that's the downside of this approach.

1 to ensure that the current object self-replication operator= has good behavior, including the "source object" and "target object" address, thoughtful statement order and COPY-AND-SWAP operation;
2 determines that any function that operates more than one object, and where multiple objects are the same object, is still behaving correctly.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.