您的位置:首页 > 编程语言 > C语言/C++

More Effective C++议题【六】:关于自增、自减操作符的一些讨论

2014-01-28 16:14 218 查看
<<More Effective C++>> 学习笔记【六】

这个议题首先讨论的是++和--操作符的重载,为了区分前缀和后缀形式,C++语言规定后缀形式有一个int类型参数,当函数被调用时,编译器传递一个0做为int参数的值给该函数。

class UPInt {
public:
UPInt& operator++();          // ++ 前缀
const UPInt operator++(int);  // ++ 后缀
UPInt& operator--();          // -- 前缀
const UPInt operator--(int);  // -- 后缀
UPInt& operator+=(int);       // += 操作符,UPInts
// 与ints 相运算
};


调用过程中:

UPInt i;
++i; // 调用 i.operator++();
i++; // 调用 i.operator++(0);
--i; // 调用 i.operator--();
i--; // 调用 i.operator--(0);


后缀操作符函数

带一个int性参数,实参=0,但不会被使用。它的参数只是用来区分前缀与后缀函数调用。
返回一个const类型。

之所以后缀运算符是返回const型参数,原因在于避免两次自增操作,如果不是const的返回值,如下代码将会有意义:

UPInt i;
i++++;                          // 两次increment后缀,错误的语法!!
//等同于:
i.operator++(0).operator++(0);  //错误的语法!!
这种做法不好的地方在于:

与内置类型行为不一致:

int类型连续自增是不允许的);

与期望的行为不一致:

行为并不会将i自增两次,而是将i自增了一次,第二个++操作则是对第一个返回的对象进行了自增,并非原来的i。

注~函数返回const型对象的一个作用

当处理用户定义的类型时,尽可能地使用前缀increment,因为它的效率较高:

为了返回一个临时对象以做为它的返回值,后缀表达式往往需要建立一个临时对象,所以为了提高效率,针对用户定义类型,应该尽量考虑使用前缀自增自减表达式。

后缀increment和decrement应该根据它们的前缀形式来实现:

为了确保后缀increment和前缀increment的行为一致,同时为了保证修改的简便性,后缀式应该通过调用前缀形式来实现。

<<More Effective C++>> 中的示例实现为:

// 前缀形式:增加后取回
UPInt& UPInt::operator++()
{
*this += 1;		// 增加
return *this; 		// 取回值
}

// 后缀形式:取回后增加
const UPInt UPInt::operator++(int)
{
UPInt oldValue = *this; // 取回值
++(*this); 		// 调用前缀式
return oldValue; 	// 返回被取回的值
}

总结要点:

对于后缀式自增自减运算符,返回值应该是常量,这样避免连续自增操作;
为了区分后缀式与前缀式自增自减运算符,需要增加一个int型参数,编译器会赋“0”,但是不需要写出参数名,以避免多数编译器的警告;
后缀式的实现应该依赖于前缀式的实现;
对用户定义类型尽量调用前缀式自增自减运算符,以节约资源;
重载后缀式自增自减运算符是函数返回const类型返回值的一个具体应用。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息