More Effective C++:不要重载的操作符
今天图老师小编要跟大家分享More Effective C++:不要重载的操作符,精心挑选的过程简单易学,喜欢的朋友一起来学习吧!
与C一样,C++使用布尔表达式简化求值法(short-circuit evaluation)。这表示一旦确定了布尔表达式的真假值,即使还有部分表达式没有被测试,布尔表达式也停止运算。例如:
char *p;
...
if ((p != 0) && (strlen(p) 10)) ...
这里不用担心当p为空时strlen无法正确运行,因为假如p不等于0的测试失败,strlen不会被调用。同样:
int rangeCheck(int index)
{
if ((index lowerBound) (index upperBound)) ...
...
}
假如index小于lowerBound,它不会与upperBound进行比较。
很早以前上述行为特性就被反复灌输给C和C++的程序员,所以他们都知道该特性。而且他们也依靠于简短求值法来写程序。例如在上述第一个代码中,当p为空指针时确保strlen不会被调用是很重要的,因为C++标准说(正如C标准所说)用空指针调用strlen,结果不确定。
C++答应根据用户定义的类型,来定制&&和操作符。方法是重载函数operator&& 和operator,你能在全局重载或每个类里重载。然而假如你想使用这种方法,你必须知道你正在极大地改变游戏规则。因为你以函数调用法替代了简短计算法。也就是说假如你重载了操作符&&,对于你来说代码是这样的:
if (eXPression1 && expression2) ...
对于编译器来说,等同于下面代码之一:
if (expression1.operator&&(expression2)) ...
// when operator&& is a
// member function
if (operator&&(expression1, expression2)) ...
// when operator&& is a
// global function
这似乎没有什么不同,但是函数调用法与简短求值法是绝对不同的。首先当函数被调用时,需要运算其所有参数,所以调用函数functions operator&& 和 operator时,两个参数都需要计算,换言之,没有采用简短计算法。第二是C++语言规范没有定义函数参数的计算顺序,所以没有办法知道表达式1与表达式2哪一个先计算。完全与具有从左参数到右参数计算顺序的简短计算法相反。
因此假如你重载&&或,就没有办法提供给程序员他们所期望和使用的行为特性,所以不要重载&&和。
同样的理由也适用于括号操作符,但是在我们深入研究它之前,我还是暂停一下,让你不要太惊奇,“逗号操作符?哪有逗号操作符?”确实存在。
逗号操作符用于组成表达式,你经常在for循环的更新部分(update part)里遇见它。例如下面