运算符重载:本质上是函数重载
C++中所有预定义的运算符都是通过运算符函数来 实现的。
例如: i +j 编译器自动解析为 operator+(i, j)
标准C++语言中已经为各种基本数据类型重载了运 算符函数op () erator+()。
这些重载形式如:
operator+(int, int)
operator+(float, float)
operator+(double, double)
根据函数重载原则,系统会用operator+(int, int)与 表达式“i+j”匹配。
“=”运算符重载不能被派生类继承
C++中可重载的运算符
不可重载运算符. (成员引用运算符) *(成员指针运算符):: ? : sizeof
重载的运算符要保持原运算符的意义。例如,单目运算 符不能重载为双目运算符;
只能对已有的运算符重载,不能增加新的运算符;
重载的运算符不会改变优先级别和结合性;
以下运算符只允许用成员函数重载:= ( ) [ ] new delete
运算符重载时,运算符函数只能定义为两种方式: 类的成员函数 友元函数
这两种方式非常相似,关键区别在于 成 员函数具有this 指针, 友元函数没有 this 指针
一元运算符,不论是前缀还是后缀,都需要一个操作数:
aa @ 及 @ aa
其中@:重载的运算符 aa:重载运算符的类的对象
可以解释为:aa . operator @ ( )
所需操作数在参数表由对象隐式提供
这时,运算 符函数用类的成员函数表示
或者可以解释为:operator @ (aa)
所需操作数在参数表由对象显式提供
这时,运算 符函数用类的友元函数表示
同样分为成员函数和友元函数两种实现方案
aa @ bb
友元函数operator(aa,bb)
成员函数aa.operator(bb)
示例 三维坐标重载
// 成员函数重载运算符,范例程序 # include < iostream > using namespace std; class three_d { int x, y, z; // 3 d di t // 3_d coordinates public: three_d operator+(three_d t); // 重载“+” three_d operator=(three_d t);// 重载“=” three_d operator++(); // 重载“++” void show(); void assign(int mx, int my, int mz); }; three_d three_d :: operator+(three_d t) // 重载“+” { three_d temp; temp.x = x + t.x; temp.y = y + t.y; temp.z = z + t.z; return temp; } three_d three_d :: operator=(three_d t)// 重载“=” { x = t.x; y = t.y; z = t.z; return *this; } three_d three_d :: operator++() // 重载一元运算符“++” { x++; y++; z++; return *this; } void three_d::show() // 显示 xyz , , 坐标 { cout << x << "," << y << "," << z << "\n"; } void three_d::assign(int mx, int my, int mz) // 指定坐标 { x = mx; y = my; z = mz; } int main() { three_d a, b, c; a.assign(1, 2, 3); b.assign(10, 10, 10); a.show(); b.show(); a . operator+(b); c = a + b; // 将 a 和 b 加在一起 c.show(); c = a + b + c; // 将 a 、b、c 加在 起一 c.show(); c = b = a; // 多重赋值 c.show(); b.show(); ++c; // 对 c 递加 c.show(); cin.ignore(); return 0; } /* 1,2,3 10,10,10 11,12,13 22,24,26 1,2,3 1,2,3 2,3,4 */
复数的重载运算 即二元运算示例
#include<iostream> using namespace std; class Complex { private: double real, image; public: Complex(double x = 0.0, double y = 0.0) { real = x; image = y; } Complex operator-(const Complex &c); // 减法重载,双元 bool operator==(const Complex &c); Complex operator-(); //取反运算符重载,单元 Complex &operator+=(const Complex &c); void Print(); }; void Complex::Print() { cout << real << " + " << image << "i" << endl; } Complex Complex::operator-(const Complex &c) // 减法重载 { Complex temp(real - c.real, image - c.image);//为什么这里可以直接访问c的私有数据成员?因为C++的封装针对的是类而不是对象。
//感觉怪怪的,本来a-b,a.operator-(b),b自己就有访问自己的私有成员的权限啊 return temp; } bool Complex:: operator==(const Complex &c) { return (real == c.real && image == c.image); } Complex Complex:: operator-() //取反运算符重载,单元 { return Complex(-real, -image); } Complex & Complex::operator+= (const Complex &c) { real += c.real; image += c.image; return *this; } int main() { Complex c1(2, 7), c2(4, 2), c3; c3 = c1 - c2; c3.Print(); if (c3 == c1) cout << "c3 equals to c1" << endl; else cout << " c3 doesn t’ equal to c1 equal to c1 endl; " << endl; c3 = -c2; c3.Print(); c3 += c2; c3.Print(); cin.ignore(); return 0; } /* -2 + 5i c3 doesn t’ equal to c1 equal to c1 endl; -4 + -2i 0 + 0i */
只是这个输出有点龙鸣
注意引用作为返回值的用法,详细见类和结构的constructing那些构造函数和析构函数的辨析
即不会产生返回值副本。
原文:https://www.cnblogs.com/theda/p/11980181.html