c++中的操作符重载

  来讲讲c++强大特性之一,操作符重载。
  中学时的数学课程学习的复数,其形式为:a + bi(a、b均为实数),其中a称为实部,b称为虚部,i称为虚数单位。复数和实数一样,可以进行加减乘除等运算。那么我们可以构建一个复数类,如下。

class ComplexNumber
{
public:
    int a;  //实部
    int b;  //虚部        
};

  根据复数运算规则,两个复数可以相加,其运算规则为实部加实部,虚部加虚部,那么下面代码可行?

class ComplexNumber
{
public:
    int a;  //实部
    int b;  //虚部    

    ComplexNumber(int a, int b)
    {
        this->a = a;
        this->b = b;
    }   
};

int main(void)
{
    ComplexNumber c1(1, 2);
    ComplexNumber c2(5, 9);
    ComplexNumber c3 = c1 + c2;

    printf("c3.a = %d, c3.b = %d\n", c3.a, c3.b);

    return 0;
}

编译自然报错:
这里写图片描述

加法操作符只能针对于实数之间,怎么可以用于对象之间。
为实现复数相加功能,我们可以定义一个成员函数Add(),专门实现此功能:

class ComplexNumber
{
private:
    int a;  //实部
    int b;  //虚部    

public:
    ComplexNumber(int a, int b)
    {
        this->a = a;
        this->b = b;
    }

    ComplexNumber Add(ComplexNumber& c1, ComplexNumber& c2)
    {
        ComplexNumber ret(c1.a + c2.a, c1.b + c2.b);
        return (ret);
    }

    int getA()
    {
        return a;   
    }

    int getB()
    {
        return b;
    }
};

int main(void)
{
    ComplexNumber c1(1, 2);
    ComplexNumber c2(5, 9);
    //ComplexNumber c3 = c1 + c2;

    ComplexNumber c3 = c1.Add(c1, c2);

    printf("c3.a = %d, c3.b = %d\n", c3.getA(), c3.getB());

    return 0;
}

考虑到数据的封装性,可以将成员变量a和b设置为private属性。
编译运行正常:
这里写图片描述

  在c++中,通过对象调用成员函数时,不要忘记还有this指针这一说(this指针可以看文章http://blog.csdn.net/qq_29344757/article/details/76427588),this指针会指向对象的自身,所以对于Add()成员函数,我们可以只传递一个ComplexNumber对象即可:

class ComplexNumber
{
    //...

    ComplexNumber Add(ComplexNumber& c)  //this指针会传来一个ComplexNumber对象,作为加数之一
    {
        ComplexNumber ret(this->a + c.a, this->b + c.b);
        return (ret);
    }

    //...
};

int main(void)
{
    //...

    ComplexNumber c3 = c1.Add(c2);

    printf("c3.a = %d, c3.b = %d\n", c3.getA(), c3.getB());
}

其运行结果和前面一样。

  成员函数Add()实现了两个复数对象的相加问题,但是c++中操作符重载特性的存在,可以让“+”支持两个复数相加,也就是让两个自定义的类类型相加。如何实现?

先看操作符重载的基本语法:

Type operator sym(const Type& c1, const Type& c2)
{
    Type ret;

    //...

    return ret;
}

  注意,operator为关键字,sym为已定义的操作符,如+,-,*,/,%,>>等等。
  通过operator定义的函数,可以为已定义的操作符拥有新的操作。稍微修改下前面的Add()函数即可:

class ComplexNumber
{
private:
    int a;  //实部
    int b;  //虚部    

public:
    ComplexNumber(int a, int b)
    {
        this->a = a;
        this->b = b;
    }

    ComplexNumber operator+ (ComplexNumber& c)
    {
        ComplexNumber ret(this->a + c.a, this->b + c.b);
        return (ret);
    }

    int getA()
    {
        return a;   
    }

    int getB()
    {
        return b;
    }
};

int main(void)
{
    ComplexNumber c1(1, 2);
    ComplexNumber c2(5, 9);
    ComplexNumber c3 = c1.operator+(c2);    //调用c1的operator+()成员函数

    //ComplexNumber c3 = c1.Add(c2);

    printf("c3.a = %d, c3.b = %d\n", c3.getA(), c3.getB());

    return 0;
}

编译运行:
这里写图片描述

这样对operator+()函数调用跟调用Add()没啥两样区别,那要是这样呢?

ComplexNumber c3 = c1 + c2;

  这样岂不是实现了两个对象直接调用“+”执行相加操作了么。c++操作符重载的强大之处在于,直接通过“+”符号,编译器会自动检索到operatorr+()函数,且能够正确匹配“+”两边的操作数。

  c++中函数重载的意义就在于扩展函数的功能,使得相同的函数名可以有其它功能,调用的时候,根据上下文(实质就是根据函数参数)调用对应的功能的函数。

  操作符重载也是类似的概念,其本质是通过函数来扩展操作符的功能,这个函数是以operator关键字加上操作符来声明定义的,如上的ComplexNumber operator+ (ComplexNumber& c)。在使用已被重载的操作符来实现对应操作时,如使用“+”实现加法操作,程序如何知道是要使用操作符的重载函数呢?也是根据上下文决定的,这个特性跟前面函数重载根据函数参数调用相对应功能函数一样。另外,全局函数和成员函数都可以实现对操作符的重载,它们最为关键的区别在于,类的成员函数,具有this指针,所以可以少一个操作数,而全局函数没有,所以需要两个操作数。

  复数类的操作不仅仅有+,还有-,*,/,=,==和!=等,依照这个例子就不难实现了。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值