(40.1)典型的运算符重载之构造分数类和典型运算符重载

文章目录

1.构造分数类

  • eg:构建一个“分数”类Fraction。
#include <iostream>
#include <stdlib.h>
using namespace std;
class Fraction { //Fraction类表示分数
	public:
		Fraction(int n=0,int d=1) : nume(n),deno(d) 
		{ 
			simplify(); //25/100转化为1/4
		}
		Fraction(double d); //double类型转换Fraction构造函数,0.251/4
		Fraction(const string& str); //string类型转换Fraction构造函数
		Fraction(const Fraction& f):nume(f.nume),deno(f.deno) { }
		//复制构造函数
		
		void display(); //显示分数
	private:
		void simplify(); //简化分数
		int nume,deno; //分子nume, 分母deno
};

Fraction::Fraction(const string& str) : nume(0),deno(1)
{ 
	//字符串"2/3"转换为分数类
	char buf[200];
	int i=str.find('/') , j=str.length()-i-1;//返回/在字符串“2/3“的位置,即:i=1
	if (i>=0) 
	{
		str.copy(buf,i,0);//0字符开始,取i个字符放到 buf
		buf[i]=0;//放个字符串结束标志
		nume=atoi(buf);//前面子串转换为分子
		
		str.copy(buf,j,i+1);
		buf[j]=0;
		deno=atoi(buf);//后面子串转换为分母
	}
	simplify();//规格化分数
}
Fraction::Fraction(double d):nume(d),deno(1)//分子初始为d的整数部份
{ 
	d=d-nume; //d的小数部分 0.25
	while ( int(d*10) != 0) 
	{ 
		// 0.25=>25/100
		nume=nume*10+int(d*10);
		deno=deno*10;
		d=d*10-int(d*10);
	}
	simplify();//规格化分数
}

void Fraction::display()
{ 
	//显式规格化的分数
	if (deno!=0&&deno!=1&&nume!=deno)
		cout<<nume<<"/"<<deno<<endl;
	else 
		cout<<nume<<endl;
		// 当出现nume/0,nume/1,nume/nume时只显示nume
}
void Fraction::simplify()
 { //分数规格化
	int m, n, r, s=1;//s为符号位,s为1为正数
	if (nume!=0 && deno!=0) 
	{ //分母不能为0
		if (deno<0) s=-s, deno=-deno; //分母取正数
		if (nume<0) s=-s, nume=-nume;
		//分子取正数, s为分数符号, 符号在分子上
		m=nume, n=deno;
		
		//下面是求最大公约数的欧几里得算法
		while(n!=0) 
		{
			r=m%n, m=n, n=r;
			//求nume和deno的最大公约数m
		}
		
		if (m!=0) 
		{
			nume=s*nume/m, deno=deno/m;
		}//分子分母去除公约数
	}
	else 
	{
		nume=0, deno=1;
		//分子或分母为0时规格化为分子=0, 分母=1
	} 
}
 int main()
 {
	 Fraction a(1,2),b(0.25),c("6/9");
	 a.display(); //输出1/2
	 b.display(); //输出1/4
	 c.display(); //输出2/3
	 return 0;
 }

发布了556 篇原创文章 · 获赞 140 · 访问量 16万+

猜你喜欢

转载自blog.csdn.net/u011436427/article/details/104221865