运算符重载例题

news/2024/10/25 17:22:11/

用的是vs2019编译器

这是一个有关运算符重载的例题,希望大家作以参考

定义有理数类(分母不为0的分数,分子分母均为整数)Rational,实现相应操作符的重载。
(1)定义私有数据成员分子int iUp ; 分母int iDown
(2)定义私有成员函数void Reduce()int Gcd(int l, int r),分别用于有理数的约简求两个整数的最大公约数。其中,在约简时需要求取分子与分母的最大公约数。
(3)定义构造函数,在构造函数体内可调用Reduce对有理数进行约简。
(4)将负号-和赋值运算符=重载为公有成员函数,分别用于求有理数的负数和赋值。
(5)将前置++、前置–、后置++、后置–重载为公有成员函数,实现有理数自增1或自减1。
(6)将+、-、*、/重载为友员函数,实现有理数的加减乘除。
(7)将<、<=、>、>=重载为友员函数,实现有理数的大小关系比较。
(8)重载流插入符<<和流提取符>>,分别用于有理数的输出和输入。其中,输出格式为“分子/分母”,若为整数,则直接输出整数。
在main函数中,根据输入的分子和分母定义两个有理数对象a和b。再定义几个有理数对象分别用于表示a和b的加、减、乘、除、前置自增a、前置自减a、后置自增a、后置自减a,并依次各个对象的结果。最后依次用<、<=、>、>=比较a和b的大小关系,并依次输出比较结果(true或false)。

输入

两个有理数a和b的的分子和分母

输出

有理数a和b的加、减、乘、除以及前置自增a、前置自减a、后置自增a、后置自减a有理数a和b的<、<=、>、>=的结果

样例输入

4 3
3 2

样例输出

a+b: 17/6
a-b: -1/6
a*b: 2
a/b: 8/9
-a: -4/3
++a: 7/3
–a: 4/3
a++: 4/3
a–: 7/3
a<b: true
a<=b: true
a>b: false
a>=b: false

下面展示此题代码

#include <iostream>
using namespace std;class Rational{friend Rational operator+(Rational& p1, Rational& p2);friend Rational operator-(Rational& p1, Rational& p2);friend Rational operator*(Rational& p1, Rational& p2);friend Rational operator/(Rational& p1, Rational& p2);friend bool operator<(Rational& p1, Rational& p2);friend bool operator<=(Rational& p1, Rational& p2);friend bool operator>(Rational& p1, Rational& p2);friend bool operator>=(Rational& p1, Rational& p2);friend ostream& operator <<(ostream& cout, Rational& p);friend istream& operator >>(istream& cin, Rational& p);
private:int iUp;int iDown;//有理数约简void Reduce() {int t = abs(Gcd(iUp, iDown));iUp = iUp / t;iDown = iDown / t;if (iDown < 0){iDown = -iDown; iUp = -iUp; }}int Gcd(int l, int r) {int temp = l % r;while (temp != 0) {l = r;r = temp;temp = l % r;}return r;}public:Rational() {iUp = 1;iDown = 1;}Rational(int a,int b) {iUp = a;iDown = b;Reduce();}//相反数Rational operator-()  { Rational temp;temp.iUp = -iUp;temp.iDown = iDown;return temp;}//赋值    Rational& operator=(const Rational& p) {iUp = p.iUp;iDown = p.iDown;Reduce();return *this;}//前置++Rational& operator++() {iUp += iDown;Reduce();return *this;}//前置--Rational& operator--() {iUp -= iDown;return *this;}//后置++Rational operator++(int) {Rational temp = *this;iUp += iDown;return temp;}//后置--Rational operator--(int) {Rational temp = *this;iUp -= iDown;return temp;}  };
//加法+
Rational operator+(Rational& p1, Rational& p2) {Rational temp;temp.iDown = p1.iDown * p2.iDown;temp.iUp = p1.iUp * p2.iDown + p2.iUp * p1.iDown;temp.Reduce();return temp;
}
//减法-
Rational operator-(Rational& p1, Rational& p2) {Rational temp;temp.iDown = p1.iDown * p2.iDown;temp.iUp = p1.iUp * p2.iDown - p2.iUp * p1.iDown;temp.Reduce();return temp;
}
//乘法*
Rational operator*(Rational& p1, Rational& p2) {Rational temp;temp.iUp = p1.iUp * p2.iUp;temp.iDown = p1.iDown * p2.iDown;temp.Reduce();return temp;
}
//除法/
Rational operator/(Rational& p1, Rational& p2) {Rational temp;temp.iUp = p1.iUp * p2.iDown;temp.iDown = p1.iDown * p2.iUp;temp.Reduce();return temp;
}
//<号
bool operator<(Rational& p1, Rational& p2) {int temp;temp = p1.iDown * p2.iDown;p1.iDown = temp;p1.iUp += p2.iDown;p2.iDown = temp;p2.iUp += p1.iDown;p1.Reduce();p2.Reduce();if (p1.iUp < p2.iUp) {return true;}return false;
}
bool operator<=(Rational& p1, Rational& p2) {int temp;temp = p1.iDown * p2.iDown;p1.iDown = temp;p1.iUp += p2.iDown;p2.iDown = temp;p2.iUp += p1.iDown;p1.Reduce();p2.Reduce();if (p1.iUp <= p2.iUp) {return true;}return false;
}
bool operator>(Rational& p1, Rational& p2) {int temp;temp = p1.iDown * p2.iDown;p1.iDown = temp;p1.iUp += p2.iDown;p2.iDown = temp;p2.iUp += p1.iDown;p1.Reduce();p2.Reduce();if (p1.iUp > p2.iUp) {return true;}return false;
}
bool operator>=(Rational& p1, Rational& p2) {int temp;temp = p1.iDown * p2.iDown;p1.iDown = temp;p1.iUp += p2.iDown;p2.iDown = temp;p2.iUp += p1.iDown;p1.Reduce();p2.Reduce();if (p1.iUp >= p2.iUp) {return true;}return false;
}
ostream& operator <<(ostream& cout, Rational& p) {int temp;if (p.iUp % p.iDown == 0) {cout << p.iUp / p.iDown <<endl;}else {cout << p.iUp << "/" << p.iDown << endl;}return cout;
}
istream& operator >>(istream& cin, Rational& p) {cin >> p.iUp >> p.iDown;//cout << p.iUp << "/" << p.iDown << endl;return cin;
}int main()
{Rational a;Rational b;cin >> a;cin >> b;Rational c;				c = a + b;cout << "a+b: " << c ;c = a - b;cout << "a-b: " << c;c = a * b;cout << "a*b: " << c;c = a / b;cout << "a/b: " << c;c = -a;cout << "-a: " << c ;cout << "++a: " << ++a ;cout << "--a: " << --a ;c = a++;cout << "a++: " << c ;c = a--;cout << "a--: " << c ;bool d;d = (a < b);cout << "a<b: " << boolalpha << d << endl;d = (a <= b);cout << "a<=b: " << boolalpha << d<< endl;d = (a > b);cout << "a>b: " << boolalpha << d << endl;d = (a >= b);cout << "a>=b: " << boolalpha << d << endl;system("pause");
}

对于这个题本人遇到的一些小问题

  1. 为什么在最后输出的时候引入了新的值cd
    因为在重载<<和>>时,传入的是一个类对象的引用。例如,若直接写成
    cout<<"a+b: "<< a + b << endl ;则会造成重载的其实是a + b这两个类对象的重载的加运算。

  2. 对于返回类类型的运算符重载来说,为什么有的返回的是类类型的引用?
    以上代码在进行加减乘除时,都在重载函数内用了临时的类类型变量temp,所以如果用返回引用的话,编译器会报错,因为temp的生命周期只是在函数内,无法传它的引用到外界。而在前置++赋值=前置– 中,返回的是传入值的本身,所以要用引用返回。

  3. 关于void Reduce()函数在每一个二元运算中的调用。
    调用的原因其实很简单,但是会很容易忽视。因为在二元运算后,可能会改变分子分母的符号,所以必须调用此函数,来调整输出,以保证如果是负数,输出时负号是在分子前面的,也可以调用此函数进行上下都是负数,从而约简成都是正数。


http://www.ppmy.cn/news/315253.html

相关文章

FPGA实现深度学习系列之卷积神经网络算法描述

这里全部内容都是由这个网址转载过来的。 https://tech.youmi.net/2016/07/163347168.html 解说&#xff1a; 关于算法的完成。需要看很多的文章和视频才能有更好的理解和领悟。这里就随便点一下。 1&#xff0c;FPGA作为部署终端&#xff0c;只执行前向传导任务。并不执行…

十字链表c语言实验报告,矩阵加法(基于十字链表)及C语言代码实现

矩阵之间能够进行加法运算的前提条件是:各矩阵的行数和列数必须相等。 在行数和列数都相等的情况下,矩阵相加的结果就是矩阵中对应位置的值相加所组成的矩阵,例如: 采用链式存储结构存储稀疏矩阵三元组的方法,称为“十字。 十字链表法表示矩阵 例如,用十字链表法表示矩阵…

万字博文讲解如何用shell来实现一个俄罗斯方块小游戏

文章目录 1.游戏效果运行图&#xff1a;2. 前置知识与游戏进程设计&#xff1a;2.1: 有关 $0,$1,$2,...$9, 和 $!2.2 进程设计 3.进程间信号传递3.1 RunAsKeyReceiver接收到用户的键盘输入后是如何把信号传递给RunAsDisplayer 进程的 4. 使用echo进行字符打印4.1 打印带颜色背景…

计算机开发日语词汇笔记二

プルダウンリスト&#xff1a;下拉列表&#xff0c;“pull-down list”。 取得できない場合、○○のプルダウンリストに値は設定されない。 不给○○下拉列表赋值。 プルダウンリストに全ての項目を表示する。 下拉列表中显示所有的列表。 エビデンス&#xff1a;成果&…

飞腾(ARM V8)平台实现FFT

最近在做飞腾上的FFT优化&#xff0c;记录一下以后用。 目前实现了基2FFT&#xff0c;使用arm提供的neon接口做了并行计算。算法原理网上很多&#xff0c;这里就不讲了&#xff0c;记录复数正向优化方法。 优化思路&#xff1a; 第一层蝶形计算&#xff1a; 第一层的蝶形因子都…

iDownsV1.8.4资源素材教程下载类WordPress

介绍&#xff1a; 本主题全部干净整洁&#xff0c;代码开源&#xff0c;可以自行随意修改。 完美适合WordPress虚拟资源分享下载站&#xff0c;或者其他的素材资源站点。 感谢支持作者&#xff0c;如果您不是在本站下载的主题&#xff0c;关于安全等任何问题本人概不负责&…

转载:全局拉普拉斯平滑之(1)Strucutre extraction from texture via relative total variation及稀疏矩阵求解...

全局拉普拉斯平滑之&#xff08;1&#xff09;Strucutre extraction from texture via relative total variation及稀疏矩阵求解 2018年01月31日 22:04:35 最近在研究图像增强处理过程中&#xff0c;阅读了关于全局拉普拉斯平滑&#xff08;global laplacian smoothing&#xf…

idown v1.3.0build 130

是一款新生代万用下载器&#xff0c;目标成为一款新生代万用下载器。适用于Win7 / Vista / Win2003 / WinXP等系统平台。iDown支持国内115、dbank、rayfile、千军万马网等多款网盘直接下载&#xff0c;支持优酷、土豆、56、新浪博客、eNet网络学院、星火视频教程等视频网下载。…