1034 有理数四则运算 (20 分)

本文档描述了一个C++程序,用于计算并以指定格式输出两个有理数的和、差、积和商。程序处理了分母为0的情况,确保结果是最简形式,并能正确处理整型溢出。关键步骤包括使用欧几里得算法进行最大公约数计算,以及根据运算结果调整输出格式。
摘要由CSDN通过智能技术生成

题目描述:

本题要求编写程序,计算 2 个有理数的和、差、积、商。

输入格式:

输入在一行中按照 a1/b1 a2/b2 的格式给出两个分数形式的有理数,其中分子和分母全是整型范围内的整数,负号只可能出现在分子前,分母不为 0。

 输入样例:

在这里插入图片描述

输出格式:

分别在 4 行中按照 有理数1 运算符 有理数2 = 结果 的格式顺序输出 2 个有理数的和、差、积、商。注意输出的每个有理数必须是该有理数的最简形式 k a/b,其中 k 是整数部分,a/b 是最简分数部分;若为负数,则须加括号;若除法分母为 0,则输出 Inf。题目保证正确的输出中没有超过整型范围的整数。

 输出样例:

在这里插入图片描述

这道题花了我很长时间,其实不是题目有多难,主要是要正确地把一个分数按题目要求表示出来。定义一个函数print_num(a,b) , a是分子,b是分母,该函数将a,b表示的分数正确打印出来。那么对于题中要输出的加减乘除四则运算:首先用这个函数将第一个和第二个分数正确打印,然后将这两个分数由运算法则计算得到的结果的分子和分母代入函数中,将结果这个分数正确打印。

一些坑:

  • 注意计算后分母为0这种特殊情况(函数中判断后打印Inf)
  • 乘积运算结果可能会出int范围,所以开始要用long long定义变量。
  • 计算得到的结果要进行化简,然后再做后面的处理。比如8/6,如果不化简,打印结果就是1 2/6 就错了。先化简的话,8/6变成4/3 再处理就得到正确结果1 1/3。
#include<iostream>
#include<algorithm> 
using namespace std; 
int gcd(long long a, long long b){
	if(b == 0)
		return a;
	else
		return gcd(b, a%b);
}
void print_num(long long a, long long b){
	if(b == 0){
		cout<<"Inf";
		return;
	}
	if(a == 0){
		cout<<"0";
		return;
	}
    bool flag = ((a < 0 && b > 0) || (a > 0 && b < 0));
	if(flag)	cout<<"(-";
	a = abs(a);b = abs(b);
	long long t = gcd(a,b);
	a /= t; b /= t;
	long long x = a/b;
	if(x != 0){
		cout<<x;
		if(a%b == 0 && flag){
			cout<<")";
			return; 
		}
		if(a%b != 0 && flag){
			cout<<" "<<a-x*b<<"/"<<b<<")";
			return;
		}
		if(a%b != 0 && flag == 0){
			cout<<" "<<a-x*b<<"/"<<b;
			return;
		}	
	}else{
		cout<<a<<"/"<<b;
		if(flag)	cout<<")";
	}
} 
int main(){
	long long a1, b1, a2, b2;
	scanf("%lld/%lld %lld/%lld",&a1, &b1, &a2, &b2); 
	//加法
	print_num(a1,b1);
	cout<<" + ";
	print_num(a2,b2);
	cout<<" = ";
	print_num(a1*b2+a2*b1, b1*b2);
	cout<<endl; 
	//减法
	print_num(a1,b1);
	cout<<" - ";
	print_num(a2,b2);
	cout<<" = ";
	print_num(a1*b2-a2*b1, b1*b2);
	cout<<endl; 
	//乘法	
	print_num(a1,b1);
	cout<<" * ";
	print_num(a2,b2);
	cout<<" = ";
	print_num(a1*a2, b1*b2);
	cout<<endl; 
	//除法 
	print_num(a1,b1);
	cout<<" / ";
	print_num(a2,b2);
	cout<<" = ";
	print_num(a1*b2, a2*b1);		
	return 0;
} 



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值