假设现在A类中有下面两个函数
A(int,int);
A :operator+(const A& a);//①
`friend A operator+(const A& a1,const A& a2);//②`
但是不能同时定义①和②,不然编译器不知道选择哪一个 。之后我们可以这样使用运算符重载了
示例1:
A a1(19,19);
A a2(19,19);
A a3;
a3=a1+a2;//①和②都可以使用
上面被转换为
a3=a1.operator+(a2);//①
a3=operator+(a1,a2);//②
示例2:
好了,现在我们假设A中又多了一个函数
A(int);
我们就可以这样了使用
A a1(19,19);
double a2=19
A a3;
a3=a1+a2;//①和②都可以使用
上面被转换成下面这样
a3=a1.operator+(a2);//① ,double类型的a2调用A(int)构造函数转化为A类型的参数
a3=operator+(a1,a2);//②,同上
Note:
如果这时候你定义了
operator int();
会产生二义性:
第一种: 调用A(int)构造函数a2变成A类型参数,然后调用operator+函数进行重载操作
第二种: 编译器把a1变成int类型变量 ,然后两个进行和操作
示例3:
还是假设A中有构造函数
A(int);
但是我们改变变量相加的先后顺序,就只有友元函数可以了
A a1(19,19);
int a2=19
A a3;
a3=a2+a1;//只有②可以使用
被转化为
a3=a2.operator+(a1);//① ,因为a2是int的变量,不能调用方法。就算定义了`operator int();`也不会转换的
a3=operator+(a2,a1);//②,double类型的a2调用A(int)构造函数转化为A类型的参数
示例4:
现在假设在A类中有如下函数
A(int);
A(int,int);
A :operator+(double );//①
friend A operator+(double ,const A& a2);//②`
示例如下
A a1(19,19);
int a2=19
A a3;
a3=a1+a2//ok
被转化为
a3=a1.operator+(a2);//调用①
a3=operator+(a1,a2);//调用②
Tips:
示例2优点是写的代码少,高效,缺点是增加了时间和内存的开销。
示例4优点是减少时间和内存开销,缺点是写的代码比较多