《More Effective C++》Rule7:千万不要重载 &&, ||, 和 ,操作符
2016-03-12 11:09
405 查看
在C++中当布尔式的真值能够确定时,不再考虑该布尔式尚未检验的部分。如:
(A)如果a = 3,那么当判断到a>0后,就确定该布尔式是真,于是就进入下一句,而不再考虑b<0的真值。
当然,C++允许用户量身打造属于自己的 && 和 || 操作符,额……,对,就是重载工作。
但是,一旦你重载了上述操作符,那么属于它们的(A)语义也就会被取代。
考虑下面的这种情况,姑且记为(情况1):
在(A)语义中,如果p为空指针,当判断到p!=nullptr时,就会结束该布尔式的判断,
因此,不会造成"&p"对空指针取值的情况。
然而,一旦重载了&&和||操作符,(A)则会被下面“函数调用的语义“代替。
一般来讲,如果你写下了这样的句子:
其一:
其二:
然而,重载之后遵循的“函数调用”语义和原本遵循的(A)语义有两大重要区别:
1、当函数调用动作被执行,所有的参数值都必须评估完成。也就是在“函数调用”语义下,
即使p == nullptr ,(情况一)也会执行(&p)操作,从而评估参数(&p) == 3的情况。毫无疑问,这是不合理的。
2、C++语言规范并没有明确定义函数调用动作各参数的评估顺序,所以没有办法知道exp1和exp2孰先孰后。
这就和(A)语义固定从左往右的评估方式形成了鲜明的对比。毋庸置疑,未经过重载的(A)语义更理想。
综上所述,请不要重载&&和||操作符。
逗号(,)操作符有着类似的情况。
表达式中如果含有逗号操作符,那么就会有这样的情况:
先计算逗号左边的表达式exp1,然后再计算逗号右边的表达式exp2,
最后整个逗号表达式的返回值是右边的表达式exp2的返回值。
因此,重载逗号操作符也会出现重载&&和||操作符同样的后果,所以,还是不要觊觎重载逗号操作符吧。
if(a > 0 || b < 0) return 0;
(A)如果a = 3,那么当判断到a>0后,就确定该布尔式是真,于是就进入下一句,而不再考虑b<0的真值。
当然,C++允许用户量身打造属于自己的 && 和 || 操作符,额……,对,就是重载工作。
但是,一旦你重载了上述操作符,那么属于它们的(A)语义也就会被取代。
考虑下面的这种情况,姑且记为(情况1):
int *p; //... ... if(p!=nullptr && (&p) == 3) { //DO Something... ... }
在(A)语义中,如果p为空指针,当判断到p!=nullptr时,就会结束该布尔式的判断,
因此,不会造成"&p"对空指针取值的情况。
然而,一旦重载了&&和||操作符,(A)则会被下面“函数调用的语义“代替。
一般来讲,如果你写下了这样的句子:
if(exp1 && exp2) ... ...编译器会视作以下两者之一:
其一:
if(exp1.operator&&(exp2)) ... ...
其二:
if(operator&&(exp1, exp2)) ... ...这看起来貌似没什么不对? = =!
然而,重载之后遵循的“函数调用”语义和原本遵循的(A)语义有两大重要区别:
1、当函数调用动作被执行,所有的参数值都必须评估完成。也就是在“函数调用”语义下,
即使p == nullptr ,(情况一)也会执行(&p)操作,从而评估参数(&p) == 3的情况。毫无疑问,这是不合理的。
2、C++语言规范并没有明确定义函数调用动作各参数的评估顺序,所以没有办法知道exp1和exp2孰先孰后。
这就和(A)语义固定从左往右的评估方式形成了鲜明的对比。毋庸置疑,未经过重载的(A)语义更理想。
综上所述,请不要重载&&和||操作符。
逗号(,)操作符有着类似的情况。
表达式中如果含有逗号操作符,那么就会有这样的情况:
x = exp1, exp2;
先计算逗号左边的表达式exp1,然后再计算逗号右边的表达式exp2,
最后整个逗号表达式的返回值是右边的表达式exp2的返回值。
因此,重载逗号操作符也会出现重载&&和||操作符同样的后果,所以,还是不要觊觎重载逗号操作符吧。
相关文章推荐
- 二进制中1的个数
- C语言堆内存管理上出现的问题,内存泄露,野指针使用,非法释放指针
- 学习C++之类与对象
- C++中的main函数
- C语言-数组
- C语言—指针数组
- C/C++函数指针(typedef简化定义)
- 大数相关计算(c语言版)
- C语言实现希尔排序
- C语言中动态申请连续的二维数组
- 归并排序 C++实现
- C++构造函数详解及显式调用构造函数
- 小白第一次学C语言
- 孙敬哲的C++上机实验1-2
- 动态链表
- C++中引用(&)的用法和应用实例
- C-C++字符输出时遇到字符'\n','\0'区别
- C-C++字符输出时遇到字符'\n','\0'区别
- c++中 vs 简单的对txt文件读写
- 第三章字符串,向量,数组