RECORDING MY FANTASY

Monday, April 02, 2007

C++复制操作 条款13

/*
* copy_operations.cpp
* 1.复制构造和复制赋值是两种不同的操作;
* 但是,在类的实现中,它们需要被放在一起,同时出现并且需要兼容.
*/

class Impl;
class Handle {
public:
//...
Handle(const Handle& ); //复制构造函数
Handle &operator = (const Handle &); //复制赋值函数

void swap(Handle &);
//...
private:
Impl *impl_;
};
/*
* 2.复制操作如此深远,以至于总是被成对的声明,具有如上所示的签名
*/

/*
* 3.对于一个类来说,如果成员形式的swap实现具有性能或者安全的优势,那么定义
* 一个swap成员函数往往是一个非常好的主意。典型的wap实现是很直观的
*/
template <typename T>
void swap(T &a, T &b)
{
T tmp;
tmp = a;
a = b;
b = tmp;
}
/*
* 它是根据T类型的复制操作来进行定义,如果T的实现很简单,这种方式就会工作的很好;
* 但如果T是一个复杂而且庞大的类,这种方式就会导致很大的开销。对于Handle类这样的类,
* 我们有更好的方式,即交换指向各自实现的指针
*/

inline void Handle::swap(Handle &that)
{
std::swap(impl_, thta.impl_);
}
/*
* 对于句柄类来说,这项技术工作的尤其好。句柄类的全部或者部分实现就是由一个
* 指向其实现的指针构成的.因此,为其编写异常安全的swap非常简单,容易实现
*/

/*
* 4.对于复制赋值的实现来说,一个微妙之处在于,复制构造的行为必须和复制赋值的行为
* 兼容,尽管它们不是相同的操作,但是它们产生的结果不应该有区别。
* 当用标准容器时,这种要求更加严格,因为标准容器的实现通常用复制构造来替代复制赋值
* 当然也就期望两种操作产生一致的结果。
*/

/*
* 一个或许更为常见的复制赋值实现具有如下的结构
*/
Handle &Handle::operator = (const Handle& that)
{
if(this != &that) {
//赋值操作
}
return *this;
}
/*这种检查一般出于正确性和效率的考虑*/

No comments: