1. 基本用法

对已有的运算符重新进行定义,赋予其新的意义,适应不同的数据类型。
运算符重载分为成员函数实现,全局函数实现。
运算符重载使用的函数名为"operator" + “运算符”,全局函数和成员函数区别在于调用和参数,以下对几个典型的运算符进行重载举例。

2. 重载分类

  1. 运算符重载:+、-、*、/;
  2. 左移运算符:<<;
  3. 递增(减)运算符:++、–;
  4. 赋值运算符:=;
  5. 关系运算符:>、<、==、>=、<=、!=;
  6. 函数调用运算符:();

3. 加号的重载(使用成员函数)

使用背景:对于两个自定义的类Card,两个卡片合成时,等级相加后减去和的1/10,不足1按照1来算。

class Card
{friend void Levelup(); // 嗯哼~
public:Card(int level, string name) :Level(level), Name(name)   // 类的初始化{cout << this->Name << "初始化成功!" << endl;}Card operator+(Card &c2) {      // 成员函数运算符重载Card temp(0, "new_card");temp.Level = (int)((this->Level + c2.Level) * 9 / 10);return temp;}
private:int Level;string Name;
};void Levelup()
{Card c1(5, "Card_1"), c2(6, "Card_2");Card c3 = c1 + c2;cout << "第一张卡等级为:" << c1.Level << ",名称为:" << c1.Name << endl;cout << "第二张卡等级为:" << c2.Level << ",名称为:" << c2.Name << endl;cout << "新卡等级为:" << c3.Level << ",名称为:" << c3.Name << endl;
}

运行截图:

4. 乘号的运算符重载(使用全局函数)

使用背景:对于一个字符串,乘以几就复制几次并输出。

#include<iostream>
#include<string>using namespace std;string operator*(string &str, int num)
{string *temp;temp = new string[sizeof(str) * num - (num - 1)];for (int i = 0; i < num; i++){*temp += str;}return *temp;
}int main()
{string str1 = "abc";string str2 = str1 * 3;        // 调用本质为string str2 = operator*(str1, 3);cout << "原本字符串:" << str1 << endl;cout << "复制之后字符串:" << str2 << endl;system("pause");return 0;
}

运行截图:

5. 递增运算符重载

class MyInt
{public:MyInt(int a):myint(a){ /* ... */ }// 重载前置运算符MyInt& operator++()        // 返回值为引用{myint++;return *this;}// 重载后置运算符MyInt operator++(int)   // 返回值为值,并且使用int占位参数{// 先记录MyInt temp = *this;//后自增myint++;// 最后返回记录值return temp;}  // 这种写法,也就决定了后置递增运算符无法进行链式编程// 通过两个运算符重载,可以更加清楚的了解到,前置运算符效率更高private:int myint;
}

6. 赋值运算符重载

对类初始化时,编译器自动重载赋值操作,用来两个类之间的赋值。但是对于编译器提供的赋值运算符重载是,浅拷贝层次的。为了满足需要,一般会在成员变量有指针的情况下考虑我们自行对赋值运算符进行重载。这里不做仔细讨论。

值得注意的是:

  • 在进行深拷贝时,注意改变的指针是否已经指向堆区的一段空间。如果有,记得先释放,后申请。(养成好习惯!);
  • 想要赋值运算符可以实现链式编程,返回值要写为自身的引用;

7. 关系运算符重载

目的是为了满足用户自定义的类之间的比较运算。

8. 函数调用运算符重载

这个运算符重载之后的使用方式非常像函数的调用,因此成为仿函数;
举例:

#include <iostream>
#include <string>using namespace std;class Print  // 定义一个类,方法只是重载了函数的调用运算符
{public:void operator()(string str){cout << str << endl;}
};void print_func(string str)   // 定义了一个打印输出的函数
{cout << str << endl;
}int main()
{Print print_class;print_class("HelloWorld!");print_func("HelloWorld!");// 由此可以看出,两者调用方式一样,因此称重载函数调用运算符这个方法为仿函数// 好处是可以将一个函数的功能,变成一种数据类型,在后面STL部分,自定义排序方法的时候会使用到这个技术。system("pause");return 0;
}

仿函数非常灵活,没有固定的写法。

9. 运算符重载注意事项

  1. 运算符重载也可以发生函数重载;
  2. 一般不会利用成员函数重载左移运算符<<,因为无法实现对象p在右侧;在重载左移运算符时,使用
osteam& operator<<(ostream &cout, 类名 p)
{ // ...return cout;
}
  1. 重载左移运算符配合友元可以实现输出自定义数据类型;
  2. 重载前置运算符时,返回值类型设置为引用可以进行链式编程;重载后置运算符时,使用占位参数来和前置运算符作以区分,返回值类型应当设置为值;

10. 放松时刻



提一嘴,这点痛苦,终于过去了。
在这儿,基本没有有意思的东西来玩,就很枯燥。不过好在都过去啦!继续加油!

C++学习日记——运算符重载相关推荐

  1. python3学习日记——运算符

    运算符 Python语言支持以下类型的运算符: 算术运算符 比较(关系)运算符 赋值运算符 逻辑运算符 位运算符 成员运算符 身份运算符 运算符优先级 下面主要讲一下成员运算符.身份运算符.逻辑运算符 ...

  2. C++实现:自定义数组类型实现相关运算符重载

    运算符重载说明 这次我们通过来自定义数组类型重载[].<<.>>.==.!=运算符来学习C++运算符重载相关知识. C++的运算符重载是C++相对于其他编程语言的一大特色. 在 ...

  3. 小甲鱼c++学习视频之运算符重载

    一.学习要点: 1.将分数定义为一个类,简化处理过程,面向对象的思维,不仅有数据,还可以对一个分数进行操作,比如约分操作,加减乘除操作. 2.类的私有成员只能通过成员函数进行访问. 3.分数的约分过程 ...

  4. 【C++】C++类的学习(三)——运算符重载与友元函数

    [fishing-pan:https://blog.csdn.net/u013921430转载请注明出处] 前言 前面的两篇博文中介绍了类的一些基本特性,今天讲一讲运算符重载和友元. 运算符重载 运算 ...

  5. C++学习笔记(九)——运算符重载

    C++学习笔记(九)--运算符重载 C++内部定义的数据类型(int , float, -)的数据操作可以用运算符号来表示,其使用形式是表达式:用户自定义的类型的数据的操作则用函数表示,其使用形式是函 ...

  6. C++ 学习 ::【基础篇:17】:C++ 类与对象:运算符重载介绍、运算符重载函数(类内与类外区别)写法及简单设计实现

    本系列 C++ 相关文章 仅为笔者学习笔记记录,用自己的理解记录学习!C++ 学习系列将分为三个阶段:基础篇.STL 篇.高阶数据结构与算法篇,相关重点内容如下: 基础篇:类与对象(涉及C++的三大特 ...

  7. C++学习笔记:(四)运算符重载 类型转换

    目录 6.运算符重载 6.1运算符重载的基本概念 6.2成员函数重载运算符 6.3友元函数重载运算符 6.4成员函数重载运算符和友元函数重载运算符比较 6.5类型转换 6.运算符重载 面向对象程序设计 ...

  8. 【C++学习笔记四】运算符重载

    当调用一个重载函数和重载运算符时,编译器通过把您所使用的参数类型和定义中的参数类型相比较,巨鼎选用最合适的定义.(重载决策) 重载运算符时带有特殊名称的函数,函数名是由关键字operator和其后要重 ...

  9. C#学习之向量运算符重载

    //未重载运算符+=,但编译通过:C#不允许重载运算符'=',但如果重载'+'运算符,编译器会自动使用'+'运算符的重载来执行'+='运算符的操作: //'-='.'*='.'&='和'/=' ...

最新文章

  1. 【 C 】对指针表达式的个人总结与思考
  2. 深入理解 C 指针阅读笔记 -- 第六章
  3. Linux 进程间通信:管道、共享内存、消息队列、信号量
  4. 【liferay】6、关于liferay中使用requestMapping映射地址提交表单
  5. 浅谈分布式存储系统的数据分布算法
  6. SpringMCV整合配置文件
  7. oracle 01102 两实例,ORA 01102
  8. Android源代码编译——编译
  9. VAF:高级Web模糊测试工具
  10. Nsight Compute内存访问常用Metrics含义理解
  11. 软件测试 之Web项目实战解析(附全套实战项目教程+视频+源码)
  12. android 盒子gpu,挑选电视盒子时CPU和GPU哪个更重要?
  13. 李广难封--有感于团队建设
  14. SQL Server 2000中的并行处理和执行计划中的位图运算符
  15. dos界面启动xampp中mysql
  16. Intel Compute Sticks 电脑棒安装Ubuntu
  17. 微信支付(小程序微信支付)
  18. ORA-03113和ORA-00204问题处理
  19. 17级智能信息处理与控制团支部大会
  20. DINE: Domain Adaptation from Single and Multiple Black-box Predictors

热门文章

  1. iPhone相机和内存警告
  2. 资产折旧期间日志表TABA
  3. Java输出九九乘法表
  4. 如何写一份牛逼的简历
  5. Hadoop大数据创建
  6. python下二进制流文件转二维码
  7. bui java,前端BUI框架表单教程
  8. python: ipython 控制台粘贴函数时 如何控制缩进?粘贴类时,如何忽略回车?
  9. Postman调用上传文件接口提示Error: read ECONNRESET
  10. CK6136数控卧式车床机械结构设计(论文+CAD图纸+开题报告+任务书+外文文献……)