• 【PAT甲级 - C++题解】1081 Rational Sum


    ✍个人博客:https://blog.csdn.net/Newin2020?spm=1011.2415.3001.5343
    📚专栏地址:PAT题解集合
    📝原题地址:题目详情 - 1081 Rational Sum (pintia.cn)
    🔑中文翻译:有理数的和
    📣专栏定位:为想考甲级PAT的小伙伴整理常考算法题解,祝大家都能取得满分!
    ❤️如果有收获的话,欢迎点赞👍收藏📁,您的支持就是我创作的最大动力💪

    1081 Rational Sum

    Given N rational numbers in the form numerator/denominator, you are supposed to calculate their sum.

    Input Specification:

    Each input file contains one test case. Each case starts with a positive integer N (≤100), followed in the next line N rational numbers a1/b1 a2/b2 ... where all the numerators and denominators are in the range of long int. If there is a negative number, then the sign must appear in front of the numerator.

    Output Specification:

    For each test case, output the sum in the simplest form integer numerator/denominator where integer is the integer part of the sum, numerator < denominator, and the numerator and the denominator have no common factor. You must output only the fractional part if the integer part is 0.

    Sample Input 1:

    5
    2/5 4/15 1/30 -2/60 8/3
    
    • 1
    • 2

    Sample Output 1:

    3 1/3
    
    • 1

    Sample Input 2:

    2
    4/3 2/3
    
    • 1
    • 2

    Sample Output 2:

    2
    
    • 1

    Sample Input 3:

    3
    1/3 -1/6 1/8
    
    • 1
    • 2

    Sample Output 3:

    7/24
    
    • 1
    题意

    给定 N 个有理数,格式为 分子/分母 ,请你计算它们的和。

    保证答案中需要出现的所有数字都在 long long 范围内,且保证最终答案为非负数。

    另外,如果给定的分数为负数,则符号在分子上。

    思路

    我们可以一个一个分数进行计算,用两个变量 ab 来计算所有计算结果。

    因为题目数据范围比较大,如果直接按照正常逻辑 a / b + c / d = ( a ∗ d + c ∗ b ) / b ∗ d a/b + c/d= (a*d+c*b)/b*d a/b+c/d=(ad+cb)/bd 计算可能会爆 int ,我们需要拆分成三步防止爆 int

    1. 先对给定的分数 c/d 进行化简。
    2. 然后进行运算,为了防止乘数过大,每次乘法前都除以一个 bd 的最大公约数。
    3. 最后再对结果 a/b 进行化简。
    代码
    #include
    using namespace std;
    
    typedef long long LL;
    
    //求最大公约数
    LL gcd(LL a, LL b)
    {
        return b ? gcd(b, a % b) : a;
    }
    
    int main()
    {
        LL a = 0, b = 1;
        int n;
        cin >> n;
        for (int i = 0; i < n; i++)
        {
            LL c, d;
            scanf("%lld/%lld", &c, &d);
    
            //先对输入的分数进行化简
            LL t = gcd(c, d);
            c = c / t, d = d / t;
    
            //乘法可能会爆int,所以计算过程中也除以个最大公约数
            t = gcd(b, d);
            a = d / t * a + b / t * c;
            b = b / t * d;
    
            //最后再对结果进行化简
            t = gcd(a, b);
            a = a / t, b = b / t;
        }
    
        if (b == 1) printf("%lld\n", a);
        else
        {
            if (a >= b)    printf("%lld ", a / b), a %= b;
            printf("%lld/%lld\n", a, b);
        }
    
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
  • 相关阅读:
    美食杰项目(六)发布菜谱
    【深度学习】python调用超分Real-ESRGAN
    Android 13.0 Launcher3仿ios长按app图标实现抖动动画开始拖拽停止动画
    性能调优MySQL 一
    nginx部署多个项目
    LuatOS-SOC接口文档(air780E)-- http - http 客户端
    MyBatis框架的搭建以及使用教程
    图片大小如何调整?分享几个快速修改图片大小的方法
    2022年湖北工业大学招生简章之高起专、专升本非全日制学历提升
    Element Plus el-form表单自定义插槽如何使用
  • 原文地址:https://blog.csdn.net/Newin2020/article/details/127638346