高精度

一般数字超过10^18就得要用高精度了,用数组存大数的每一位,然后模拟加减乘除运算的过程。不过要注意前导零

高精度加法:

 

 

模板题:Luogu A+B Problem(高精)

题目描述

高精度加法,相当于a+b problem,不用考虑负数.

输入格式

分两行输入。a,b <= 10^500

输出格式

输出只有一行,代表a+b的值

 

代码及注释:

复制代码
#include <iostream>
#include <cstring>
using namespace std;
const int N = 510;
int a[N], b[N], c[N];
char A[N], B[N];

int main()
{
    scanf("%s%s", A, B);
    int len1 = strlen(A), len2 = strlen(B), len3 = max(len1, len2) + 1;  // len3 是结果的最大长度 因为可能两数相加不进位 所以以防万一 要+1 
    for(int i = 0; i < len1; i++) a[len1 - i] = A[i] - '0';  // 倒着存 
    for(int i = 0; i < len2; i++) b[len2 - i] = B[i] - '0';
    
    for(int i = 1; i <= len3; i++)
    {
        c[i] += a[i] + b[i];   
        c[i+1] = c[i] / 10;  // 进位到下一位 
        c[i] = c[i] % 10; 
    }
    if(c[len3] == 0 && len3 > 1) len3--;  // 消除前导0  加法的话 只可能出现一个前导0 因为如果不进位的话 就只有一个位置是空的 
    
    for(int i = len3; i > 0; i--) cout << c[i]; // 倒着输出 
    
    return 0;
}
复制代码

 

高精度减法:

 

 

要点:1、如果a < b 则需要交换a,b,最后在结果上加负号,判断a是否大于b的函数如下:

复制代码
bool check(char a[], char b[])
{
    if(strlen(a) != strlen(b)) return strlen(a) > strlen(b);
    for(int i = strlen(a) - 1; i >= 0; i--)
    if(a[i] != b[i]) return a[i] > b[i];
    
    return true;
}
复制代码

 

   2、如果a[i] < b[i] 则需向高位借1当10用,代码如下:

     

if(a[i] < b[i])
{
    a[i] += 10;
    a[i+1] --;
}
    c[i] = a[i] - b[i];

 

模板题:Luogu A+B Problem(高精)

题目描述

高精度减法。

输入格式

两个整数 a,b(第二个可能比第一个大)。

0 < a,b < 10^10086

输出格式

结果(是负数要输出负号)。

 

代码及注释:

复制代码
#include <iostream>
#include <cstring>
using namespace std;
const int N = 100010;
int a[N], b[N], c[N];
char A[N], B[N];

bool check(char a[], char b[])  // 判断函数 
{
    if(strlen(a) != strlen(b)) return strlen(a) > strlen(b);
    for(int i = strlen(a) - 1; i >= 0; i--)
    if(a[i] != b[i]) return a[i] > b[i];
    
    return true;
}

int main()
{
    scanf("%s%s", A, B);
    int len1 = strlen(A), len2 = strlen(B), len3 = max(len1, len2); // 减法 结果的位数不可能高于这两个数的位数 
    for(int i = 0; i < len1; i++) a[len1 - i] = A[i] - '0';
    for(int i = 0; i < len2; i++) b[len2 - i] = B[i] - '0';
    
    if(check(A, B))   // 如果A > B 就让 A - B 
    {
        for(int i = 1; i <= len3; i++)
        {
            if(a[i] < b[i])
            {
                a[i] += 10;
                a[i+1] --;
            }
            c[i] = a[i] - b[i];
        }
        while(c[len3] == 0 && len3 > 1) len3--;
        for(int i = len3; i > 0; i--) cout << c[i];
    }
    else  // 否则 就是 B - A 最后加 负号 
    {
        for(int i = 1; i <= len3; i++)
        {
            if(b[i] < a[i])
            {
                b[i] += 10;
                b[i+1] --;
            }
            c[i] = b[i] - a[i];
        }
        while(c[len3] == 0 && len3 > 1) len3--;
        cout << "-";
        for(int i = len3; i > 0; i--) cout << c[i];
    }
    return 0;
}
复制代码

 

高精度乘法:

 

 

要点: 1.   a[1] * b[1] 对应 c[1] 的位置

     a[2] * b[2] 对应 c[2] 的位置

     a[3] * b[3] 对应 c[3] 的位置

     ......

     发现规律: a[i] * b[j] 对应 c[i + j - 1] 的位置

       2.   考虑进位。 代码如下:

c[i + j - 1] += a[i] * b[j];
c[i + j] += c[i + j - 1] / 10;
c[i + j - 1] %= 10;

 

模板题:Luogu A*B Problem

题目描述

求两数的积。

输入格式

两行,两个整数。

输出格式

一行一个整数表示乘积。

说明/提示

每个数字不超过 10^2000,需用高精。

 

代码及注释:

复制代码
#include <iostream>
#include <cstring>
using namespace std;
const int N = 210;
int a[N], b[N], c[2*N];
char A[N], B[N];

int main()
{
    scanf("%s%s", A, B);
    int len1 = strlen(A), len2 = strlen(B), len3 = len1 + len2;  // len3 不超过该两位数位之和~ 
    for(int i = 0; i < len1; i++) a[len1 - i] = A[i] - '0';
    for(int i = 0; i < len2; i++) b[len2 - i] = B[i] - '0';
    
    for(int i = 1; i <= len1; i ++)
    {
        for(int j = 1; j <= len2; j++)
        {
            c[i + j - 1] += a[i] * b[j];   // 注意是 += 为什么呢? 因为可能c[i + j - 1]后一位进位了 
            c[i + j] += c[i + j - 1] / 10;  // 进位 
            c[i + j - 1] %= 10; 
        }
    }
    
    while(c[len3] == 0 && len3 > 1) len3--;   // 去除前导零 
    
    for(int i = len3; i > 0; i--) cout << c[i];
    
    return 0; 
} 
复制代码

 

高精度除法(高精度除以低精度)

 

 要点 高精度除法不需要将数组逆置了!!!

模板题 Luogu  A/B Problem

题目描述

输入两个整数 a,b输出它们的商

输入格式

两行,第一行是被除数,第二行是除数。

输出格式

一行,商的整数部分。

说明/提示

0 <= a <= 10^5000, 0 <= b <= 9*10^9

 

代码及注释:

复制代码
#include <iostream>
#include <cstring>
using namespace std;
const int N = 5010;
typedef long long LL;   // 题目要求 
LL a[N], b, c[N];
char A[N];

int main()
{
    scanf("%s", A);
    cin >> b;
    LL len1 = strlen(A), t = 0;
    for(int i = 1; i <= len1; i++) a[i] = A[i-1] - '0';   // 除法就不需要逆置了 
    for(int i = 1; i <= len1; i++)
    {
        c[i] = (t * 10 + a[i]) / b;     // 模拟一遍
        t = (t * 10 + a[i]) % b;
    }
    LL len2 = 1;
    while(c[len2] == 0 && len2 < len1) len2++;   // 模拟一遍 
    
    for(int i = len2; i <= len1; i++) cout << c[i];
    
    return 0;
} 
复制代码

 

posted @   飘向远方丶  阅读(246)  评论(0编辑  收藏  举报
(评论功能已被禁用)
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?
· 如何调用 DeepSeek 的自然语言处理 API 接口并集成到在线客服系统
· 【译】Visual Studio 中新的强大生产力特性
· 2025年我用 Compose 写了一个 Todo App
点击右上角即可分享
微信分享提示