更新时间:2022-10-03 13:57:10
《Effective C++》 读书笔记之二 构造/析构/赋值运算
条款10:令赋值(assignment)操作符返回一个reference to *this。
例子:
1
2
3
4
5
|
Widget& operator=( const Widget& rhs)
{ ...
return * this ; //返回*this
} |
2016-11-03 09:36:00
条款11:在operator= 中处理“自我赋值”。
例子:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
|
class Widget{
...
void swap(Widget& rhs); //交换*this与rhs的数据
...
}; //第一种合理安全的写法 Widget& Widget::operator=( const Widget& rhs)
{ BitMap * pOrg = pb; //记住原先的pb
pb = new BitMap(*rhs.pb); //令pb指向*pb的一个复件(副本)
delete pOrg; //删除原先的pb
return * this ;
} //第二种合理安全的写法 Widget& Widget::operator=( const Widget& rhs)
{ Widget temp(rhs);
swap(temp);
return * this ;
} |
重点:
确保当对象自我赋值时operator= 有良好行为。其中技术包括比较“来源对象”与“目标对象”的地址、精心周到的语句顺序、以及copy-and-swap。
确定任何函数如果操作一个以上的对象,而其中多个对象是同一个对象时,其行为仍然正确。
2016-11-03 10:23:50
条款12:复制对象时勿忘其每一个成分。Copy all parts of an object.
例子:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
|
void logCall( const std::string& funcName);
class Customer{
public :
Customer( const Customer& rhs);.
Customer& operator=( const Customer& rhs);
private :
std::string name;
}; Customer::Customer( const Customer& rhs)
:name(rhs.name) //复制所有成员,防止局部拷贝(partial copy )
{ logCall( "Customer copy constructor" );
} Customer& Customer::operator=( const Customer& rhs)
{ logCall( "Customer copy assignment operator" );
name = rhs.name;
return * this ;
} class PriorityCustmer: public Custmer //一个derived class
{ public :
PriorityCustomer( const PriorityCustomer& rhs);
PriorityCustomer& operator=( const PriorityCustomer& rhs);
private :
int priority
}; PriorityCustomer::PriorityCustomer( const PriorityCustomer& rhs)
:Customer(rhs), //调用base class的copy构造函数,如果不调用,会调用Customer的default构造函数
priority(rhs.priority)
{ logCall( "PriorityCustomer copy constructor" );
} PriorityCustomer& PriorityCustomer::operator=( const PriorityCustomer& rhs)
{ logCall( "PriorityCustomer copy assignment operator" );
Customer::operator=(rhs); //对base class成分进行赋值动作
priority=rhs.priority;
return * this ;
} |
重点:
Copying函数应该确保复制“对象内的所有成员变量”及“所有base class成分”。
不要尝试以某个copying函数实现另一个copying函数。应该将共同机能放进第三个函数中,比如init(),并由两个copying函数共同调用。