表示分数的结构体
// 分数结构体 struct Fraction{ long long up, down; // 分子和分母,由于分数的乘法和除法可能使分子或分母超过int型表示范围,因此一般情况下,分子和分母应当使用long long 型来存储 };
分数的化简:
化简规则:(1)如果分子up为0, 令分母为1
(2)约分,求出分子和分母的最大公约数,然后令分子和分母同时除以这个数
(3)如果分母为负数,令分子up和分母down都变为相反数
// 求最大公约数的函数 long long gcd(long long a, long long b){ return !b ? a : gcd(b, a % b); }
// 分数的化简 Fraction reduction(Fraction result){ // 如果分子up为0, 令分母为1 if (result.up == 0){ result.down = 1; } else{ // 约分,求出分子和分母的最大公约数,然后令分子和分母同时除以这个数 long long d = gcd(abs(result.up), abs(result.down)); result.up /= d; result.down /= d; } // 如果分母为负数,令分子up和分母down都变为相反数 if (result.down < 0){ result.down = (-1) * result.down; result.up = (-1) * result.up; } return result; }
分数的加法:
// 分数的加法 Fraction add(Fraction f1, Fraction f2){ Fraction result; result.up = f1.up * f2.down + f2.up * f1.down; result.down = f1.down * f2.down; return result; }
分数的减法:
// 分数的减法 Fraction minus(Fraction f1, Fraction f2){ Fraction result; result.down = f1.down * f2.down; result.up = f1.up * f2.down - f2.up * f1.down; return result; }
分数的乘法:
// 分数的乘法 Fraction multi(Fraction f1, Fraction f2){ Fraction result; result.up = f1.up * f2.up; result.down = f1.down * f2.down; return result; }
分数的除法:(除数是否为0放在函数外部判断)
// 分数的除法 Fraction divide(Fraction f1, Fraction f2){ Fraction result; result.up = f1.up * f2.down; result.down = f1.down * f2.up; return result; }
分数的格式输出:
(1)分母为1则输出整数
(2)分子的绝对值大于分母则输出带假分数的形式
(3)真分数直接输出
// 分数的输出 void showResult(Fraction r){ // 输出前化简 r = reduction(r); // 分母为1则输出整数 if (r.down == 1){ printf("%lld", r.up); } else if(abs(r.up) > r.down){ // 分子的绝对值大于分母则输出带假分数的形式 printf("%lld %lld/%lld", r.up / r.down, abs(r.up) % r.down, r.down); } else{ // 真分数直接输出 printf("%lld/%lld", r.up, r.down); } }
题目实战:
1034 有理数四则运算 (20分)本题要求编写程序,计算 2 个有理数的和、差、积、商。
输入格式:
输入在一行中按照 a1/b1 a2/b2
的格式给出两个分数形式的有理数,其中分子和分母全是整型范围内的整数,负号只可能出现在分子前,分母不为 0。
输出格式:
分别在 4 行中按照 有理数1 运算符 有理数2 = 结果
的格式顺序输出 2 个有理数的和、差、积、商。注意输出的每个有理数必须是该有理数的最简形式 k a/b
,其中 k
是整数部分,a/b
是最简分数部分;若为负数,则须加括号;若除法分母为 0,则输出 Inf
。题目保证正确的输出中没有超过整型范围的整数。
输入样例 1:
2/3 -4/2
输出样例 1:
2/3 + (-2) = (-1 1/3)
2/3 - (-2) = 2 2/3
2/3 * (-2) = (-1 1/3)
2/3 / (-2) = (-1/3)
输入样例 2:
5/3 0/6
输出样例 2:
1 2/3 + 0 = 1 2/3
1 2/3 - 0 = 1 2/3
1 2/3 * 0 = 0
1 2/3 / 0 = Inf
代码:
1 // 分数的四则运算 2 #include <stdio.h> 3 #include <algorithm> 4 5 // 分数结构体 6 struct Fraction{ 7 long long up, down; // 分子和分母,由于分数的乘法和除法可能使分子或分母超过int型表示范围,因此一般情况下,分子和分母应当使用long long 型来存储 8 }; 9 10 // 求最大公约数的函数 11 long long gcd(long long a, long long b){ 12 return !b ? a : gcd(b, a % b); 13 } 14 15 // 分数的化简 16 Fraction reduction(Fraction result){ 17 // 如果分母为负数,令分子up和分母down都变为相反数 18 if (result.down < 0){ 19 result.down = (-1) * result.down; 20 result.up = (-1) * result.up; 21 } 22 // 如果分子up为0, 令分母为1 23 if (result.up == 0){ 24 result.down = 1; 25 } 26 else{ 27 // 约分,求出分子和分母的最大公约数,然后令分子和分母同时除以这个数 28 long long d = gcd(abs(result.up), abs(result.down)); 29 result.up /= d; 30 result.down /= d; 31 } 32 return result; 33 } 34 35 // 分数的加法 36 Fraction add(Fraction f1, Fraction f2){ 37 Fraction result; 38 result.up = f1.up * f2.down + f2.up * f1.down; 39 result.down = f1.down * f2.down; 40 return reduction(result); 41 } 42 43 // 分数的减法 44 Fraction minus(Fraction f1, Fraction f2){ 45 Fraction result; 46 result.down = f1.down * f2.down; 47 result.up = f1.up * f2.down - f2.up * f1.down; 48 return reduction(result); 49 } 50 51 // 分数的乘法 52 Fraction multi(Fraction f1, Fraction f2){ 53 Fraction result; 54 result.up = f1.up * f2.up; 55 result.down = f1.down * f2.down; 56 return reduction(result); 57 } 58 59 // 分数的除法 60 Fraction divide(Fraction f1, Fraction f2){ 61 Fraction result; 62 result.up = f1.up * f2.down; 63 result.down = f1.down * f2.up; 64 return reduction(result); 65 } 66 67 // 分数的输出 68 void showResult(Fraction r){ 69 // 输出前化简 70 r = reduction(r); 71 if (r.up < 0){ // 输出左括号 72 printf("("); 73 } 74 // 分母为1则输出整数 75 if (r.down == 1){ 76 printf("%lld", r.up); 77 } 78 else if(abs(r.up) > r.down){ 79 // 分子的绝对值大于分母则输出带假分数的形式 80 printf("%lld %lld/%lld", r.up / r.down, abs(r.up) % r.down, r.down); 81 } 82 else{ 83 // 真分数直接输出 84 printf("%lld/%lld", r.up, r.down); 85 } 86 if (r.up < 0){ // 输出右括号 87 printf(")"); 88 } 89 } 90 91 int main() 92 { 93 // 读取输入 94 freopen("in.txt", "r", stdin); 95 Fraction a, b, result; 96 scanf("%lld/%lld %lld/%lld", &a.up, &a.down, &b.up, &b.down); 97 // 计算和然后输出 98 showResult(a); 99 printf(" + "); 100 showResult(b); 101 printf(" = "); 102 result = add(a, b); 103 showResult(result); 104 printf("\n"); 105 106 // 计算差然后输出 107 result = minus(a, b); 108 showResult(a); 109 printf(" - "); 110 showResult(b); 111 printf(" = "); 112 showResult(result); 113 printf("\n"); 114 115 // 计算积然后输出 116 result = multi(a, b); 117 showResult(a); 118 printf(" * "); 119 showResult(b); 120 printf(" = "); 121 showResult(result); 122 printf("\n"); 123 124 // 计算商然后输出 125 showResult(a); 126 printf(" / "); 127 showResult(b); 128 printf(" = "); 129 if (b.up == 0){ 130 printf("Inf"); 131 } 132 else{ 133 result = divide(a, b); 134 showResult(result); 135 } 136 137 fclose(stdin); 138 return 0; 139 }