所谓重载,就是赋予新的含义。
² 函数重载(Function Overloading)可以让一个函数名有多种功能,在不同情况下进行不同的操作。
² 运算符重载(Operator Overloading)也是一个道理,同一个运算符可以有不同的功能。
例如,+号可以对不同类型(int、float 等)的数据进行加法操作;<<既是位移运算符,又可以配合 cout 向控制台输出数据。C++ 本身已经对这些运算符进行了重载。
下面的代码定义了一个复数类,通过运算符重载,可以用+号实现复数的加法运算:
1. #include
2. usingnamespace std;
3.
4. classcomplex{
5. public:
6. complex();
7. complex(double real, double imag);
8. public:
9. //声明运算符重载
10. complex operator+(const complex &A)const;
11. void display() const;
12. private:
13. double m_real; //实部
14. double m_imag; //虚部
15. };
16.
17. complex::complex():m_real(0.0), m_imag(0.0){ }
18. complex::complex(doublereal, double imag): m_real(real), m_imag(imag){ }
19.
20. //实现运算符重载
21. complexcomplex::operator+(const complex &A) const{
22. complex B;
23. B.m_real = this->m_real + A.m_real;
24. B.m_imag = this->m_imag + A.m_imag;
25. return B;
26. }
27.
28. voidcomplex::display() const{
29. cout<
30. }
31.
32. intmain(){
33. complex c1(4.3, 5.8);
34. complex c2(2.4, 3.7);
35. complex c3;
36. c3 = c1 + c2;
37. c3.display();
38.
39. return 0;
40. }
运行结果:
6.7 + 9.5i
运算符重载其实就是定义一个函数,在函数体内实现想要的功能,当用到该运算符时,编译器会自动调用这个函数。也就是说,运算符重载是通过函数实现的,它本质上是函数重载。
运算符重载的格式为:
返回值类型 operator 运算符名称 (形参表列){
//TODO:
}
operator是关键字,专门用于定义重载运算符的函数。我们可以将operator 运算符名称这一部分看做函数名,对于上面的代码,函数名就是operator+。
运算符重载函数除了函数名有特定的格式,其它地方和普通函数并没有区别。
上面的例子中, complex 类中重载了运算符+,该重载只对 complex 对象有效。当执行c3 = c1 + c2;语句时,编译器检测到+号左边(+号具有左结合性,所以先检测左边)是一个 complex 对象,就会调用成员函数operator+(),也就是转换为下面的形式:
c3 = c1.operator+(c2);
c1 是要调用函数的对象,c2 是函数的实参。
上面的运算符重载还可以有更加简练的定义形式:
1. complexcomplex::operator+(const complex &A)const{
2. return complex(this->m_real + A.m_real,this->m_imag + A.m_imag);
3. }
return 语句中的complex(this->m_real+ A.m_real, this->m_imag + A.m_imag)会创建一个临时对象,这个对象没有名称,是一个匿名对象。在创建临时对象过程中调用构造函数,return 语句将该临时对象作为函数返回值。
在全局范围内重载运算符
运算符重载函数不仅可以作为类的成员函数,还可以作为全局函数。更改上面的代码,在全局范围内重载+,实现复数的加法运算:
1. #include
2. usingnamespace std;
3.
4. classcomplex{
5. public:
6. complex();
7. complex(double real, double imag);
8. public:
9. void display() const;
10. //声明为友元函数
11. friend complex operator+(const complex&A, const complex &B);
12. private:
13. double m_real;
14. double m_imag;
15. };
16.
17. complexoperator+(const complex &A, const complex &B);
18.
19. complex::complex():m_real(0.0), m_imag(0.0){ }
20. complex::complex(doublereal, double imag): m_real(real), m_imag(imag){ }
21. voidcomplex::display() const{
22. cout<
23. }
24.
25. //在全局范围内重载+
26. complexoperator+(const complex &A, const complex &B){
27. complex C;
28. C.m_real = A.m_real + B.m_real;
29. C.m_imag = A.m_imag + B.m_imag;
30. return C;
31. }
32.
33. intmain(){
34. complex c1(4.3, 5.8);
35. complex c2(2.4, 3.7);
36. complex c3;
37. c3 = c1 + c2;
38. c3.display();
39.
40. return 0;
41. }
运算符重载函数不是 complex 类的成员函数,但是却用到了 complex 类的 private 成员变量,所以必须在 complex 类中将该函数声明为友元函数。
当执行c3 = c1 + c2;语句时,编译器检测到+号两边都是 complex 对象,就会转换为类似下面的函数调用:
c3 = operator+(c1, c2);