• 【3003】&&【9105】高精度求积 【高精度压位】


    高精度求积

    Time Limit: 10 second
    Memory Limit: 2 MB

    问题描述
    输入两个高精度正整数m和n(m和n均小于100位),求这两个高精度的积

    Input

    文件输入两行,第一行输入m的值,第二行输入n的值

    Output

    输出积,最后不带任何符号(不用换行)

    Sample Input

    36
    3
    

    Sample Output

    108
    

    【题解】

    代码提供的是4位的压位。5位压位会导致一个点通过不了。应该是做乘法的时候溢出了。用了unsigned long long 。。。

    【代码】

    提供一张图片供理解。

    #include <cstdio>
    #include <string>
    #include <iostream>
    
    using namespace std;
    
    const int MAXN = 800;
    
    string s1,s2;
    int l1,l2,l3;
    unsigned long long  ta[MAXN],tb[MAXN],a[MAXN],b[MAXN],c[MAXN];
    
    void input_data()
    {
        cin >> s1;
        cin >> s2;
        l1 = s1.size();
        l2 = s2.size();
        for (int i = 1;i <= l1;i++) //ta和tb用于以不压位的形式存储输入的数据
            ta[i] = s1[l1-i] - '0';
        for (int i = 1;i <= l2;i++)
            tb[i] = s2[l2-i] - '0';
        for (int i = 1;i <= l1 / 4;i++) //4个数字4个数字地存入相应的a和b数组.
            a[i] = ta[4*i]*1000 + ta[4*i-1]*100 + ta[4*i-2]*10 + ta[4*i-3];
        int a1 = l1 / 4;
        int d = l1 % 4; //有时候不会刚好数的长度为4的倍数,会有剩下的。直接放到最后面。
        if (d != 0)
            {
                int now = 0;
                for (int i= 1; i <= d;i++) //获取剩余的数字
                        now = now*10 + ta[l1-i+1];
                a1++;
                a[a1] = now;//存入a数组中
            }
        for (int i = 1;i <= l2 / 4;i++) //b数组也是同样的步骤
            b[i] = tb[4*i]*1000 + tb[4*i-1]*100 + tb[4*i-2]*10 + tb[4*i-3];
        int b1 = l2 / 4;
        int re = l2 % 4;
        if (re != 0)
            {
                    int dd = 0;
                    for (int i = 1;i <= re;i++)
                        dd = dd*10 + tb[l2-i+1];
                    b1++;
                    b[b1] = dd;
            }
        l3 = l1 + l2 ;
    }
    
    void get_ans()
    {
        for (int i = 1 ;i <= MAXN - 20;i++)
            c[i] = 0;
        for (int i = 1;i <= l1;i++)
            for (int j = 1;j <= l2;j++)
                c[i+j-1] = c[i+j-1] + a[i]*b[j]; //c[i+j-1]+=a[i]*b[j] 这是高精度乘法的通用步骤
        for (int i = 1;i <= l3;i++) //接下来开始进位,和普通的高精度乘法有所不同。
            if (c[i] >= 10000)
                {
                    c[i+1] = c[i+1] + (c[i] / 10000);
                    c[i] = c[i] % 10000;
                }
        while (c[l3+1] >0)
            {
                l3++;
                c[l3+1] = c[l3+1] + (c[l3] / 10000);
                c[l3] = c[l3] / 10000;
            }
        while (c[l3]==0 && l3>0) l3--; //防止位数超过了实际位数。做一下检验工作。
    }
    
    void output_ans()
    {
        printf("%d",c[l3]); //最高位前面是不会有多余的0的,所以直接输出。如a[1]=462 a[2]=56  l3=2 a[l3] = 56 这个时候你不能在56前面加0.而465前要加0
        //最后结果就是560462
        for (int i = l3-1;i >= 1;i--) //控制一下输出就可以了。
            {
                if (c[i] >= 1000)
                    {
                        printf("%d",c[i]);
                        continue;
                    }
                if (c[i] >= 100)
                    {
                        printf("0%d",c[i]);
                        continue;
                    }
                if (c[i] >= 10)
                    {
                        printf("00%d",c[i]);
                        continue;
                    }
                if (c[i] >=1)
                    {
                        printf("000%d",c[i]);
                    }
                printf("0000");
            }
    }
    
    int main()
    {
        input_data();
        get_ans();
        output_ans();
        return 0;
    }
    


     

  • 相关阅读:
    链表的一些规律总结
    acclib的尝试
    初入指针
    在一个堆成矩阵中的循环判断(井字棋游戏)
    初学c语言的小套路汇总
    在循环中计算式一正一负的处理
    最大公约数的计算方法
    大数加法
    大数乘法
    复制可见区域到新表
  • 原文地址:https://www.cnblogs.com/AWCXV/p/7632487.html
Copyright © 2020-2023  润新知