您的位置:首页 > 编程语言 > C语言/C++

【C++】c++复数类Complex

2015-10-03 11:20 656 查看

运算符重载应该注意以下几个问题:

(1)c++语言中只能对已有的c++运算符进行重载,不允许用户自己定义新的运算符。

(2)c++中绝大部分的运算符允许重载,不能重载的运算符只有以下几个:

. 成员访问运算符

.* 成员指针访问运算符

:: 作用域运算符

sizeof 长度运算符

?: 条件运算符

(3)重载不能改变运算符的操作对象(即操作数)的个数。例如,在c++语言中,运算符“+”是一个双目运算符(即只能带两个操作数),重载后仍为双目运算符。

(4)重载不能改变运算符原有的优先级,也不能改变运算符原有的结合特性。例如,c++语言规定,乘法运算符“/”的优先级高于减法运算符“-”的优先级,故表达式:x = a/b-c; 的集合特性等价于 x = (a/b)-c;。

(5)运算符重载函数的参数至少应有一个是类对象(或类对象的引用),即运算符重载函数不能全是c++预定义的基本数据类型。例如:

int operator+ (int x,int y)

{ return x+y; }

int operator+ (int x,int y)

{ return x-y; }

以上两个函数构成了重载,如果有表达式:5+3,它的结果是8呢?还是2呢?显然,这是绝对不允许的!

(6)双目运算符一般可以被重载为友元运算符重载函数或者成员运算符重载函数,但有一种情况,必须使用友元函数!

例如:如果将一个类AB的对象与一个整数相加,可以用成员运算符函数重载“+”运算符。

AB::operator+ (int x)

{

AB tmp;

tmp.a = a+x;

tmp.b = b+x;

return tmp;

}

若ob1和ob2是类AB的对象,则以下语句是正确的:

ob2 = ob1+200;这条语句被c++编译系统解释为:ob2 = ob1.operator+ (200);

由于对象ob2是运算符“+”的左操作数,所以它可以调用“+”运算符重载函数operator+(),执行结果是ob1数据成员a和b都加上一个整数200。然而,以下语句就不能工作了:

ob2 = 200 + ob1;这条语句被c++编译系统解释为:ob2 = 200.operator+(ob1);

由于运算符“+”的左操作数是一个整数200,而不是该类对象,不能调用该类的成员运算符重载函数,所以编译时会出错。如果定义以下两个友元运算符重载函数:

friend AB operator+ (AB ob,itn x); //运算符”+”的左侧是类对象,右侧是整数

friend AB operator+ (itn x,AB ob); //运算符”+”的左侧是整数,右侧是类对象

当类AB的一个对象与一个整数相加时,无论整数出现在左侧还是右侧,使用友元运算符重载函数都能得到很好的解决。

下面是将运算符重载成成员运算符重载函数:

class Complex
{
public:
/*************复数类Complex默认成员函数*********************/
Complex(double real = 0.0, double image = 0.0)       //构造函数
{
_real = real;
_image = image;
}
Complex(const Complex& c)                            //拷贝构造函数
{
_real = c._real;
_image = c._image;
}
Complex& operator= (const Complex& c)                //赋值操作符重载
{
if (this != &c)//防止自赋值
{
_real = c._real;
_image = c._image;
}
return *this;
}
~Complex()                                          //析构函数
{}
/*************复数类Complex基本操作函数*********************/
void Display()                                      //打印复数
{
cout << "_real  : " << _real << "  ";
cout << "_image : " << _image << endl;
}
Complex operator+ (const Complex& c)               //+运算符重载
{//不能返回临时变量的引用
Complex tmp;
tmp._real = _real + c._real;
tmp._image = _image + c._image;
return tmp;
}
Complex operator- (const Complex& c)               //-运算符重载
{
Complex tmp;
tmp._real = _real - c._real;  //测试当相减为负数时
tmp._image = _image - c._image;
return tmp;
}
Complex& operator+= (const Complex& c)            //+=运算符重载
{
_real += c._real;//把+=后的结果赋给_real,即this的值发生改变
_image += c._image;
return *this;
}
Complex& operator-= (const Complex& c)            //-=运算符重载
{
_real -= c._real;//把-=后的结果赋给_real,即this的值发生改变
_image -= c._image;
return *this;
}
Complex operator++ (int)                           //后置++
{//这里的int类型参数只是用来区别后缀“++”与前缀“++”,此外没有任何作用
Complex tmp(*this);
_real++;//(*this)._real++;只需对实部加1
return tmp;
}
Complex& operator++()                              //前置++
{
_real++;
return *this;
}
Complex operator-- (int)                           //后置--
{
Complex tmp = *this;//调用拷贝构造函数
_real--;
return tmp;
}
Complex& operator-- ()                             //前置--
{
_real--;
return *this;
}
Complex operator*(const Complex& c)//(ac-bd)+(bc+ad)i
{
Complex tmp;
tmp._real = (_real*c._real) - (_image*c._image);
tmp._image = (_image*c._real) + (_real*c._image);
return tmp;
}
Complex operator/(const Complex& c)//(bc-ad)/(c^2+d^2)i
{
Complex tmp;
tmp._real =(_image*c._real) - (_real*c._image);
tmp._image = pow(c._real, 2) + pow( c._image, 2);
return tmp;
}
private:
double _real;     //实部
double _image;    //虚部
};


总结:

是否将运算符重载成友元运算符重载函数,决定权在于你。谨慎一点的话,建议重载成友元运算符重载函数。

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: