关闭

7. 千万不要重载&& ,|| 和,操作符

标签: deletenull编译器语言编程c
759人阅读 评论(0) 收藏 举报
分类:

C/C++语言对于逻辑表达式具有“逻辑短路”的性质,即一旦确定了真假值,表达式中即使有尚未检查的部分,都将返回。如:


char *p;
if ((p != NULL) && printf("%c", *p)) ...                     //(1)
    
int rangeCheck(int index)
{
    if ((index < lowerBound) || (index > upperBound)) ...    //(2)
    ...
}

(1)中你不用担心p为NULL时,调用printf函数会出现错误,因为一旦p为NULL逻辑与的检测将返回FASLE,无需计算后面的部分。

(2)中检查下标值是否越界,你也不用担心如果index已经越下界还会与上界进行比较,因为前者正确之后即返回TRUE,无需计算后者。

 

当我们进行重载&&和||时,我们也希望具有上面的性质。但事与愿违,多数情况是无法达到这种要求。如我们将operator &&重载,当我们写出如下的表达式:

if (expression1 && expresssion2)    ...

//编译器会视作:

if (expression1.operator&&(expression2))   ...          //operator&& 是member-function

//或者

if (operator&&(expression1, expression2))  ...          //operator&& 是global-function

上面两种形式,都会将计算expression1和expression2的值,而且计算的顺序也不确定,这样就违背了之前谈论的“逻辑短路”现象。

 

逗号(,)操作符的含义,是从左到右依次计算每个表达式的值,最后返回的是最后一个表达式的值,如

expression1, expression2, ..., expressionN;

将依次计算expression1,expression2,...的值,最后返回值为expressionN的值。

现在我们重载逗号(,)操作符,如果是以global-function形式给出,我们无法确保参数的计算顺序是从左到右的;如果以member-function形式给出,仍不能保证逗号操作符的左操作数先被计算。因此,不能确保完成逗号操作符所期望的功能。

 

现总结C++语言中不能重载的操作符有:

.            .*             ::           ?:
new          delete         sizeof       typeid
static_cast  dynamic_cast   const_cast   reinterpret_cast
可以重载的操作符有:
operator new      operator delete
operator new[]    operator delete[]
+   -   *   /   %   ^   &   |   ~
!   =   <   >   +=  -=  *=  /=  %=
^=  &=  |=  <<  >>  >>= <<= ==  !=
<=  >=  &&  ||  ++  --  ,   ->*  ->
() [] 
 
参考文献: 《More Effective C++ 35个改善编程与设计的有效方法 中文版》
 
1
0
查看评论
发表评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场

C++ STL 基础及应用(2) 模板与操作符重载

模板是 C++ 语言中重要的概念。它提供了一种通用的方法来开发重用的代码,即以创建参数化的 C++ 类型。 本章将阐述一些具体的 STL 模板思想,并简单介绍操作符重载与模板的联系。 文中将给出一个简易的类似 vector 的数组类。
  • Raito__
  • Raito__
  • 2016-05-22 17:13
  • 2561

C++运算符重载(11) - 重载<<和>>操作符

运算符 “>”用于流输出。 在开始重载这些操作符之前,必须注意下面的事项: 1) cout是输出类的对象,而cin是输入类的对象 2) 这些操作符必须重载为全局函数。如果想要让它们可以访问私有成员,则必须定义为友元。 为何必须重载为全局函数? 如果操作符重载为一个成员函数...
  • shltsh
  • shltsh
  • 2015-05-27 00:11
  • 788

探索Scala(1)-- 运算符重载

Scala语言运算符重载完全是语法层面的小把戏,本文记录我对Scala语言运算符重载的一些理解
  • SpiderDog
  • SpiderDog
  • 2014-10-14 14:39
  • 3324

Kotlin操作符重载(十)

Kotin操作符重载
  • learningITwell
  • learningITwell
  • 2017-06-08 20:16
  • 285

C++运算符重载(4) - 不能被重载的操作符

C++,中,下面的操作符是不能被重载的: . (成员访问或点操作符) ?: (三元操作符或条件操作符) :: (范围操作符) .* (指向成员的指针操作符) sizeof (取对象大小操作符) typeid (对象类型操作符) 更多参考: http://en.wikibook...
  • shltsh
  • shltsh
  • 2015-05-26 09:39
  • 2122

Kotlin开发Android笔记9:Kotlin操作符重载

Kotin有一些固定数量象征性的操作符,开发中可以在任何类中使用它们。使用方法是: 创建一个方法,方法名为保留的操作符关键字,如此就可以让这个操作符的行为映射到这个方法。重载这些操作符可以增加代码可读性和简洁性。 —操作符表——- 下面是一系列包括操作符和对应方法的表。对应方法必...
  • true100
  • true100
  • 2016-08-11 14:01
  • 1287

C++中的重载运算符、继承、封装、多态讲解(进阶篇)

上次我们说到C++语言中的面向对象基本概念,那就是什么是类什么是对象,他们之间的关系是什么,本篇博文我们来说说,C++语言中重要的几个机制。(面试也经常会被问到这些知识点) 一个类可以派生自多个类(和Java不同,Java只能继承一个类),这意味着,它可以从多个基类继承数据和函数。定义一个派...
  • songkai320
  • songkai320
  • 2016-07-15 10:16
  • 1080

所有C++操作符重载的例子

1.[ ]操作符重载 C++语言规定:“[ ]”只能作为类的成员函数进行重载。 “[ ]”是C++中的下标运算符,对于数组或指针来说,下表运算的语义是确定的,不能进行重载。因此,如果看到一个运算结果不是数组或指针的表达式后跟“[ ]”运算符,一定是对“[ ]”进行了重载。 一个例子: ...
  • chijianxingfeng
  • chijianxingfeng
  • 2013-04-30 13:04
  • 2392

New运算符的重载

首先我们要清楚,为什么我们要重载new,和delete了?这还不是指针造成的,确实指针是一件让人喜欢的东西,用起来如此让人喜欢,让人顺手。然而小程序我们完全可以避免内存泄露问题,大程序就不那么容易了,然而我们有一种特别好的方法可以跟踪我们new,和delete动作,找到未被释放的内存。办法是什么呢?...
  • ghevinn
  • ghevinn
  • 2014-01-16 15:32
  • 5818

C++ 重载操作符 operator

参数个数的限定     非成员函数:   单目运算符:参数表中只有一个参数;   双目运算符:参数表中只有两个参数       成员函数:   单目运算符:参数表中没有参数;   双目运算符:参数...
  • fenhong91
  • fenhong91
  • 2017-02-07 09:55
  • 842
    个人资料
    • 访问:361642次
    • 积分:3385
    • 等级:
    • 排名:第11525名
    • 原创:73篇
    • 转载:0篇
    • 译文:6篇
    • 评论:92条
    公告
    最新评论
    友情链接