`
lc52520
  • 浏览: 369286 次
  • 性别: Icon_minigender_1
  • 来自: 成都
社区版块
存档分类
最新评论

操作符重载

阅读更多
      什么是操作符重载?

  一看到重载,很容易就让人联想到成员函数重载,函数重载可以使名称相同的函数具有不同的实际功能,只要赋给这些同名函数不同的参数就可以了,操作符重载也是基于这一机制的。系统为我们提供了许多操作符,比如“+”,“[ ]”等,这些操作符都有一些默认的功能,而操作符重载机制允许我们给这些操作符赋予不同的功能,并能够按照普通操作符的使用格式来使用自己定义功能的操作符(即重载的操作符)。

  定义之后,我们就可以按照平常使用操作符的格式来使用我们自己的重载操作符了。

  操作符重载一般在类内部定义,就像成员函数一样定义,这叫做类成员重载操作符。当然也可以在类外定义,即非类成员操作符重载。

  为什么要使用操作符重载?

  举例说明,比如类String,该类有这样一个功能,可以将两个字符串连接成一个字符串,为此,我们可以给类String定义一个成员函数实现此功能,可以给该函数取一个形象的名字,比如concatenate或append,但是相比较,这两个名字都不如操作符“+=”形象直观。在这种情况下,我们就可以定义操作符“+=”的重载,来实现此功能。

  也就是说,如果要定义一个函数,而这个函数的功能与操作符的功能比较类似时,这个时候我们就可以定义重载操作符,而不使用通常的成员函数定义。这里所说的操作符重载,指的是与系统定义的操作符重载,而不是说定义两个“+=”,这两个重载,这一点需要清楚。

  但是这四个操作符不能用于重载::: .* . ?:

  如何声明操作符重载?

  同普通函数类似,只不过它的名字包括关键字operator,以及紧随其后的一个预定义操作符。例如:

  String& operator+=(const String&);

  String& operator+=(const char*);

  注意:上面的括号表示形式参数,即使操作符重载不需要参数,也应该写上一个空的“( )”,而不是将其省略,这一点其实和普通函数的声明是类似的。其实,声明的唯一区别就是名字不同而已。

  怎样使用操作符重载?

  两种操作符重载:类成员操作符重载和非类成员操作符重载。

  1、类成员操作符重载

  已知类String中声明了两个“==”操作符重载,分别是:

  bool operator==(const char*) const;

  bool operator==(const String&) const;

  其中第一个重载的操作符允许我们比较一个String类对象是否等于一个C风格字符串,第二个允许我们比较两个String类对象是否相等。

  示例代码

  :

  #include<String.h>

  int main()

  {

  String flower;

  If(flower==”lily”) //正确:调用bool operator==(const char*) const;

  ……

  else

  if(“tulip”==flower) //错误

  …….

  }

  关键看一下,为什么第二个重载操作符的使用是错误的?

  因为:只有在左操作数是该类类型的对象时,才会考虑使用作为类成员的重载操作符。

  因为这里的”tulip”不是String类型对象,所以编译器试图找到一个内置操作符,它可以有一个C风格字符串的左操作数,然而事实上并不存在这样的操作符,所以编译时产生错误。

  疑问:我们可以使用String类的构造函数将一个C风格字符串,转换成一个String对象,为什么编译器不能做以上转换呢?即

  if(String(“tulip”)==flower);//这样就是正确的

  答:为了效率和正确性

  重载操作符并不要求两个操作数的类型一定相同。可能有这样一个类Text,这个类的构造函数的参数及其成员重载操作符的参数都与String类一致,如果使编译器能够自动将C风格字符串转换成某个类型的对象,那么编译器首先会检索所有的类定义,选择能够提供正确构造函数和重载操作符的类进行转换,这无疑会增加程序的编译时间,还有就是类String和类Text均合适,编译器也不知道该将C风格字符串转换成String还是Text对象了。

  对于类成员重载操作符,隐式的this指针被用作隐式的第一个参数,对于成员操作符,flower==”lily”会被编译器重写为:flower.operator==(“lily”);

  2、非类成员操作符重载

  为了解决上面的问题,我们可以考虑使用非类成员操作符代替类成员操作符,这样做的好处是左操作数不必非要是某个类的类型对象了,对于需要两个操作数的操作符重载,我们就可以定义两个参数了。比如:

  bool operator==(const String&,const String&);

  bool operator==(const String&,const char*);

  可以看到,这两个全局重载操作符比成员操作符多了一个参数,这样定义之后,还是上面的代码,当调用flower==”lily”时,会调用上面的bool operator==(const String&,const char*);

  然而“tulip”==flower会调用哪个操作符重载呢,我们并没有定义bool operator==(const char*,const String&);,我们是不是必须定义这样一个全局操作符重载呢?答案是否定的,因为当一个重载操作符是一个名字空间函数时,对于操作符的第一个和第二个参数,即等于操作符的左右两个操作数都会考虑转换,就像int vi=1; double vd=2.0; vi=vi+vd; 会先将vd转换成int型,再做加法一样这意味着,编译器将解释第二个用法如下:

  bool operator==(String(“tulip”),flower)。这样会增加系统转换开销。

  因此,如果需要频繁比较C风格字符串和String对象,那么最好定义上面的操作符重载,如果不频繁,我们只需定义下面一个就够了:

  bool operator==(const String&,const String&);

  什么时候定义类成员操作符重载,什么时候定义非类成员操作符重载?

  答:(1)如果一个重载操作符是类成员,那么只有当跟它一起使用的左操作数是该类对象时,它才会被调用,如果该操作符的左操作数必须是其他类型,那么重载操作符必须是非类成员操作符重载。

  (2)C++要求,赋值(=),下标([ ]),调用(())和成员访问箭头(->)操作符必须被指定为类成员操作符,否则错误。
分享到:
评论

相关推荐

    C++ 操作符重载

    在C++编程语言中,操作符重载是一种特殊的功能,允许程序员为已有的运算符赋予新的含义,以便在自定义类型上使用。这使得代码更加直观和自然,尤其是在处理复杂数据结构时。本主题将深入探讨操作符重载的概念、语法...

    类应用举例 操作符重载

    标题中的“类应用举例 操作符重载”意味着接下来的内容将围绕如何在类中实现操作符重载的概念来举例说明。操作符重载是面向对象编程中的一个重要概念,它允许程序员为类定义特定的操作符的行为,使得这些操作符能够...

    实现操作符重载 实现操作符重载

    在C++编程语言中,操作符重载是一种重要的特性,它允许我们为自定义类型定义已有的运算符的行为。操作符重载并不意味着创建新的运算符,而是为现有的运算符赋予新的含义,使得它们可以作用于自定义类型的对象。本文...

    分数类中的操作符重载

    在C++编程中,操作符重载是一种强大的特性,它允许我们为自定义类型赋予标准操作符的行为。在这个“分数类”中,我们看到开发者已经实现了对基本分数类的操作符重载,使得分数对象可以像内置类型(如整数或浮点数)...

    C++编写的操作符重载实例

    ### C++操作符重载实例解析 #### 一、引言 操作符重载是C++语言中的一个重要特性,它允许我们对已有的操作符赋予新的含义,使其能够用于自定义的数据类型。本文将通过一个具体的例子——分数类的操作符重载——来...

    Kotlin学习教程之操作符重载详解

    由于你无法修改已有的接口定义,因此一般可以通过 扩展函数 来为现有的类增添新的 约定方法,从而使得 操作符重载 这一语法糖适应任何现有的 Java 类。 算术运算符 我们就从最简单直接的例子 + 这一类算术运算符...

    快速排序算法测试,操作符重载,模板应用

    总结来说,这个项目重点在于理解和实现快速排序算法,通过操作符重载提供灵活的比较方式,利用模板实现泛型排序,确保代码能在不同的数据类型上工作,并且所有这些都在Visual Studio 2005环境下进行了测试和调试。...

    C++操作符重载

    在C++编程语言中,操作符重载是一种特殊的功能,允许程序员为已有的运算符赋予新的含义,以便在用户自定义的数据类型上使用。这使得我们可以以自然且直观的方式处理对象,增强了代码的可读性。操作符重载并不创建新...

    C++操作符重载专题

    ### C++操作符重载专题 #### 一、引言 C++作为一种强大的面向对象编程语言,提供了多种机制来帮助开发者构建复杂的应用程序。其中一项关键特性便是**操作符重载**。通过这一特性,开发者能够对现有操作符赋予新的...

    操作符重载详解

    在C++编程语言中,操作符重载是一种特殊的功能,允许我们为已有的运算符赋予新的含义,以便在自定义数据类型上使用。这使得我们可以按照与内置类型(如整数或浮点数)类似的语法来操作我们自己定义的对象。操作符...

    c++操作符重载

    ### C++操作符重载详解 C++是一种强大的面向对象编程语言,提供了众多特性来增强其功能性和灵活性,其中操作符重载就是一项关键特性。本文将深入探讨C++中的操作符重载,包括其基本概念、重载规则以及如何在实际...

    C++操作符重载手册

    在C++编程语言中,操作符重载是一项关键特性,允许程序员为自定义类型赋予与内置类型相似的操作符行为。本手册将详细阐述C++中操作符重载的相关规则、建议以及如何重载`operator new`。 **一、操作符重载规则** 1....

    C++操作符重载专题 超高清 超详细

    操作符重载是C++编程语言中一种强大的特性,它允许开发者为自定义类型赋予常用操作符如加、减、乘、除等新的含义。通过操作符重载,我们可以像操作基本数据类型一样操作自定义的对象,这不仅提高了代码的可读性和...

    利用操作符重载,对时间操作的应用程序

    在编程领域,操作符重载(Operator Overloading)是一种C++和某些其他编程语言中的特性,允许我们为自定义类型赋予特定的操作符含义。在这个"利用操作符重载,对时间操作的应用程序"中,开发者可能创建了一个自定义...

    39114_20170620200252_C++操作符重载_

    在C++编程语言中,操作符重载是一种特殊的功能,允许我们为自定义类型赋予与内置类型(如整型或浮点型)相同的操作符含义。通过操作符重载,我们可以使用户定义的类更加直观和易用,因为它能够遵循程序员熟悉的运算...

    19操作符重载[参照].pdf

    【操作符重载】是C#编程中的一种高级特性,允许程序员为自定义类型赋予特定操作符的新功能,以便在类或结构中更加自然地表达计算逻辑。在.NET框架下,操作符重载有助于增强代码的可读性和简洁性。 19.1 理解操作符 ...

    19操作符重载[归类].pdf

    操作符重载是C#语言中的一种特性,它允许程序员为自定义数据类型定义操作符的行为,以便这些操作符在处理这些类型时能符合预期的逻辑。操作符重载主要涉及以下几个方面: 1. **操作符重载的概念**:操作符重载是...

    c++(6)操作符重载

    ### 操作符重载:C++中的赋值运算符与比较运算符 #### 一、赋值运算符重载 在C++编程语言中,赋值运算符`=`用于将一个对象的值复制到另一个对象中。对于基本数据类型如整型、浮点型等,这种复制通常是直接且无害的...

Global site tag (gtag.js) - Google Analytics