运算符重载

运算符重载

实质:是函数的重载

作用:扩展了原有运算符的功能

通过函数来实现复数相加 eg:

 

在add函数中没有对象名的是隐藏了this指针,返回值类型是类类型因为我们所存的数据是对象名所以返回值是类类型。

但是这里在调用的时候不方便用户进行使用,因为我们需要打出c3=c1.complex_add(c2);

所以我们就想办法就是可不可以就像使用c3=c1+c2;一样方便客户使用呢

因此就有了运算符重载,也可以理解就是它的作用就是扩展了原有运算符的功能。

重载运算符函数一般格式如下:

函数类型 operator 运算符名称 (形参表)

{对运算符的重载处理}

比如,我们想将“+“用于Complex类(复数)的加法运算,函数的原型可以是这样的:

Complex operator+(Complex& c1,Complex& c2);

说明:其实和定义普通函数如出一辙,Complex是我们的返回值类型(类类型)operator+是函数名,(这里面就是类类型的参数列表,当然也可以是其他类型看需求写就行)。

作为成员函数的重载函数实现复数相加 eg:(强调了是成员函数,后面会有和友元函数区分)

 

在编译器里其实28行会被计算机里写成函数调用的,c3=c1.operator+(c2);

从代码的14行处看,我们只有一个对象作为参数,是因为我们成员函数具有this指针在函数体内没有对象名的就是我们调用的时候的当前对象,那么我们在重载运算符的主函数中的体现就是在第一个操作数也就是c1,那么我们也能知道如果操作数是整型或者其它类型,总之不是本类对象的都不能写在第一个操作数,第一个操作数必须要是本类对象,第二个操作数是什么就是靠我们自己编写了,就像14行我们的形参列表里是存储类类型的对象所以我们第二个操作数就是类类型,倘若换成整型就要修改,如下:

 

14行我们就修改成了整型变量的引用,所以我们在28行使用的时候就是可以加上整型数据,特别注意的是16行中我们显示使用this指针可以加上括号,不然可能会报错.

我们运算符重载可以定义多个,毕竟运算符重载就是为了扩充我们运算符的功能,我们定义越多不同的用法那么这个运算符就会越丰富,如我们同时写出对整型相加和类类型相加:

 

总结:使用运算符重载作为函数成员时,我们必须得保证第一个操作数是本类对象,第二个操作数就是看在定义运算符重载函数时你所给在形参表中的类型了。

运算符重载函数作为友元函数

这里就开始与作为成员函数的运算符重载函数做区别了。

先看代码:

 

改成了友元函数,在14行代码中我们可以清晰的看到变成了俩个类类型的对象作为参数,为何变的不是一个参数了呢,因为友元函数不存在this指针没有当前对象的功能。

在28行我们调用了作为友元函数的运算符重载函数,系统会编译器内部其实也依旧是调用函数的方式去实现c3=operator+(c1,c2);

为什么要将运算符重载函数作为友元函数呢,首先我们知道作为成员函数的时候第一个操作数必须是本类对象,那么如果我们实现一个程序第一个必须是整型的时候就得使用友元函数,倘若我们能够使用成员函数就尽量使用成员函数,毕竟友元函数破坏了对象的封装性。

注意:当我们定义一个运算符重载函数作为友元函数的时候,如果在形参列表中第一个是整型变量,第二个是类类型变量时,我们在使用的时候也得遵循这个顺序,倘若你想不管前后哪个是整型变量都可以运行时就多定义一个运算符重载函数即可。代码:

 

就像代码中第6行,我们的形参列表中第一个是类类型的对象,第二个是整型变量,所以我们在后面调用的时候第一个操作数就必须得是本类对象,第二个操作数是整型。

重载运算符的规则:

  1. C++不允许用户自己定义新的运算符,只能对已有的C++运算符进行重载。
  2. C++允许重载的运算符有:

C++中可以重载的操作符有以下一些:

算术运算符:+、-、*、/、%

关系运算符:==、!=、>、<、>=、<=

逻辑运算符:&&、||、!

位运算符:&、|、^、~、<<、>>

赋值运算符:=、+=、-=、*=、/=、%=、&=、|=、^=、<<=、>>=

下标运算符:[]

前缀和后缀运算符:++、--

函数调用运算符:()

逗号运算符:,

三目运算符:? :

不能重载的有5个:

.(成员访问运算符)

*(成员指针访问运算符)

::(域运算符)

sizeof(长度运算符)

?:(条件运算符)

(3).重载不能改变运算符运算对象(即操作数)的个数。

(4).重载不能改变运算符的结合性。

(5).重载运算符的函数不能有默认的参数。

(6).重载不能改变运算符的优先级别。、

(7).重载的运算符必须和用户定义的自定义类型的对象一起使用,其参数至少应有一个是类对象(或类对象的引用)

(8).用于类对象的运算符一般必须重载,但有俩个例外,运算符“=“和”&“不必用户重载。

(9).从理论上说,可以将一个运算符重载为执行任意的操作,但是我们应当使重载运算符的功能类似于该运算符作用与标准类型数据时所实现的功能。

以下是规定大多数运算符是定义成成员函数还是友元函数

(1).C++规定,赋值运算符“=“,下标运算符”[ ]“,函数调用运算符”( )“,成员运算符”->“必须作为成员函数重载。

(2).一般将单目运算符和复合运算符(+=,-=,/=,*=,&=,!=,^=,%=,>>=,<<=)重载为成员函数。

(3).流插入“<<“和流提取运算符”>>”,类型转换运算符函数不能定义为类的成员函数,只能作为友元函数。

(4).一般将双目运算符重载为友元函数。

重载流插入运算符“<<“和流提取运算符”>>“

如果想用它们输出和输入自己声明的类型的数据,是不能直接用“<<“和”>>“来输入输出的,如果想用它们输出和输入自己声明的类型的数据,必须对它们重载。

对“<<“和”>>”重载的函数形式如下:
istream & operator>>(istream &,自定义类&);

ostream & operator<<(ostream &,自定义类&);

其实定义也与普通函数很想,ostream,istream是返回值类型(系统类类型)&(这个注意别忘记)operator<<,operator>>是函数名,(ostream&依旧是类型,自定义类&)

由上面运算符重载的规则可知道,流运算符只能定义为友元函数,但是为什么呢?

因为:1. 实际上流操作符左侧必须为cin或cout,即istream或ostream类(系统类),我们无法修改的类导致我们不能使用成员函数重载,只能使用类外的普通函数重载。

2. 由于我们将类内部的私有成员进行输入和输出,所以重载函数必须有对内部成员访问的权限,这导致我们不能使用普通的函数重载,只能使用友元函数重载。代码:

21行就是对流插入运算符进行定义,我们将output定义为引用参数名,然后在函数体内进行输出我们想对类对象输出的方式,然后返回output(为什么要返回output,因为我们要进行连续的输出,所以我们再返回output也就是返回cout刚好接受返回值也是系统类ostream,因此可以进行连续输出)[其实output就是调用时的cout,对象就是第二个参数]

同样,对流提取运算符>>重载

代码:

 

 

注意流提取运算符变成了>>别习惯性写成其它形式,在函数体内就是对想输入的对象数值进行填充,返回值就是input,接受类型为系统类istream。[当然和插入运算符一样,input代指的是cin,第二个操作数就是对象,这样可以进行对象的连续输入]。

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值