大数的加减乘除

C语言实现:

最基本的一个运算,可以用数组或指针做
一.加法

1.自己的代码,真是一点都不简洁,水平有限啊!

#include<stdio.h>
#include<string.h>

int max(int len1, int len2)
{
    return len1 > len2 ? len1 : len2;
}
int main()
{
    char s1[100], s2[100],s3[100];
    int s[500];
    int len1, len2;
    scanf("%s%s", s1,s2);
    len1 = strlen(s1);
    len2 = strlen(s2);
    if (len1 >= len2)
        {//s2在复制时会变动,导致后面的数赋值为前面已经赋值过的值,所以
            memcpy(s3, s2, sizeof(s2));//引入s3数组保留前面的值
            for (int i = 0; i < len2; i++)
            {
                s2[i + len1 - len2] = s3[i];
            }
            for (int i = 0; i < len1 - len2; i++)
                s2[i] = '0';
        }
    if (len1 < len2)
        {
            memcpy(s3, s1, sizeof(s1));
            for (int i = 0; i < len1; i++)
            {
                s1[i + len1 - len2] = s3[i];
            }
            for (int i = 0; i < len2 - len1;i++)
                s1[i] = '0';
        }
    int n = max(len1, len2) - 1;
    s[n] = (s1[n] + s2[n]-96)%10;
    for (int i = n-1; i >= 0; i--)
    {
        s[i] = (s1[i] + s2[i]-96) % 10 + (s1[i + 1] + s2[i + 1]-96) / 10;
    }
    for (int i = 0; i <= n; i++)
        printf("%d", s[i]);
    printf("\n");
return 0;
}

2.网上的代码(POJ1503)
可以计算多个相加并且简洁,膜拜

#include <stdio.h>
#include <stdlib.h>
#include<string.h>

char s[101];
int sum[101];

int main() 
{
    int i, j;
    while (gets(s), strcmp(s, "0")) //利用strcmp比较输入s是否为0,为0就结束,类似return 0;
    {//巧妙化解开多少个数组 算多少个数的和的局面
        j=strlen(s);
        for (i=j-1; i>=0; --i)
        {
            sum[j-i-1]+=(s[i]-'0');//s[i]-'0'表示字符数字转化成int数字  倒序加到sum中 sum第一个数是s的最后一个数的和
        }
    }
    j=101-1;             //这里要-1,否则后面sum[j]数组越界
    while(!sum[j]) --j;  //重新赋值j 使j为目前sum的总位数
    for (i=0;i<j;++i) 
    {   //如果sum[i]加成两位数 将十位数加给前一位数
        sum[i+1]+=sum[i]/10;
        sum[i]=sum[i]%10;
    }
    for (i=j; i>=0; --i) 
    {
        printf("%d", sum[i]);
    }
    printf("\n");
    return 0;
}

二.减法
1.自己写的代码
还是写的又臭又长,无奈,代码水平有限,不过应该可以改进,懒得弄了

#include<stdio.h>
#include<string.h>
char s1[100], s2[100];
int a[100] = { 0 }, b[100] = { 0 };
int sum[200] = { 0 };

//分开来讨论,都先较大数减较小数
void more(int n1, int n2)//第一个数长度大于第二个数
{
    for (int i = 0; i < n1; i++)
    {
        if (a[i] < b[i])
        {
            sum[i] = 10 + a[i] - b[i];
            a[i + 1]--;
        }
        else
            sum[i] = a[i] - b[i];
    }
    for (int i = n1 - 1; i >= 0; i--)
        printf("%d", sum[i]);
    printf("\n");
}

void less(int n1, int n2)//第一个数长度小于第二个数
{
    for (int i = 0; i < n2; i++)
    {
        if (b[i] < a[i])
        {
            sum[i] = 10 + b[i] - a[i];
            b[i + 1]--;
        }
        else
            sum[i] = b[i] - a[i];
    }
    printf("-"); //前面加一个负号
    for (int i = n2 - 1; i >= 0; i--)
        printf("%d", sum[i]);
    printf("\n");
}

int main()
{
    scanf("%s%s", s1, s2);
    int n1 = strlen(s1), n2 = strlen(s2);
    for (int i = 0; i < n1; i++)
        a[i] = s1[n1 - i-1]-'0';
    for (int i = 0; i < n2; i++)
        b[i] = s2[n2 - i-1]-'0';
    if (n1 > n2)
        more(n1, n2);
    else if (n1 < n2)
        less(n1, n2);
    else  //长度相同就判断大小
    {
       int m = strcmp(s1, s2);
        if (m == -1)
           less(n1, n2);
        else if (m == 1)
           more(n1, n2);
        else
           printf("0\n");
        }
return 0;   
}

看了一下网上的代码好像也没有特别简洁的,感觉我这写的也不错了

三:乘法
要点:
1.乘法中有个规则:假如结果的下标为m
sum[m]=a[0]*b[m]+a[1]*b[m-1]+a[2]*b[m-2]……a[m]*b[0]
2.先将所有的数加到一起得到所有的sum[m],再对sum进行进位操作
即跟上面大数的加法的大神代码思路一致
第一点我想到了,然而第二点没想到,做半天做不出,无奈,代码转换能力太差
下面的代码是在网上的代码的基础上改的,原先的有点小错误

#include<stdio.h>
#include<string.h>
int main()
{
    char a[2000], b[2000];
    int ans1[2000], ans2[2000], ans[4000];
    int i, j;
    memset(ans1, 0, sizeof(ans1));//必须先全赋值为0防止干扰
    memset(ans2, 0, sizeof(ans2));
    memset(ans, 0, sizeof(ans));
    scanf("%s%s", a, b);
    int len1 = strlen(a);
    int len2 = strlen(b);
    if (len1 > len2)  //确保第二个数位数较小
    {        //先倒序得到数字的数组
        for (i = len1 - 1; i >= 0; i--)
            ans1[len1 - 1 - i] = a[i]-48;
        for (i = len2 - 1; i >= 0; i--)
            ans2[len2 - 1 - i] = b[i]-48;
    }
    else //确保ans2位数比ans1小
    {
        for (i = len1 - 1; i >= 0; i--)
            ans2[len1 - 1 - i] = a[i]-48;
        for (i = len2 - 1; i >= 0; i--)
            ans1[len2 - 1 - i] = b[i]-48;
    }
    if (len1 < len2)//确保len2是比较小的数,这样好理清思路
    {
        int t;
        t = len2;
        len2 = len1;
        len1 = t;
    }
    for (i = 0; i < len2; i++)  //这里牵涉到一些数学知识如上
        for (j = 0; j < len1; j++)
        {  
           ans[j + i] += ans1[j] * ans2[i];
           if (ans[i+j] >= 10)
           {
              ans[i +j+ 1] += ans[i+j] / 10;
           }
           ans[i+j] = ans[i+j] % 10;
        }
    if(ans[len1+len2-1]!=0)  //判断最前面的那个是否为0,为0则跳过
        printf("%d",ans[len1+len2-1]);
    for (i = len1+len2 - 2; i >= 0; i--)
    {
        printf("%d", ans[i]);
    }
    printf("\n");
    return 0;
}

C++类实现:

学了一年了,现在可以用C++的类来实现这个问题,感觉还是有挺大进步的。

#include<iostream>
#include<cstring>
#include<cctype>
#include<string>
#include<vector>
#include<algorithm>
using namespace std;

class bignumber
{
private:
    static const int BASE= 1e8;
    static const int WIDTH = 8;
    vector<int> s;
public:
    bignumber(long long num = 0) { *this = num; }
    bignumber operator=(long long num)
    {
        s.clear();
        do
        {
            s.push_back(num%BASE);
            num /= WIDTH;
        } while (num > 0);
        return *this;
    }
    bignumber operator=(const string &str)
    {
        s.clear();
        int x, len = (str.length() - 1) / WIDTH + 1;
        for (int i = 0; i < len; i++)
        {
            int end = str.length() - i*WIDTH;
            int start = max(0, end - WIDTH);
            sscanf(str.substr(start, end - start).c_str(), "%d", &x);
            s.push_back(x);
        }
        return *this;
    }
    friend ostream & operator<<(ostream &os, const bignumber &x)
    {
        for (int i = x.s.size() - 1; i >= 0; i--)
            cout << x.s[i];
        return os;
    }
    friend istream & operator >> (istream &is, bignumber &x)
    {
        string s;
        if (!(is >> s))//读取失败
            return is;
        x = s;
        return is;
    }
    //四则运算
    bignumber operator+(const bignumber &b) const
    {
        bignumber c;
        c.s.clear();
        int last = 0;//上一次运算剩下的值,也就是进位值
        for (int i = 0;; i++)
        {
            if (last == 0 && i >= b.s.size() && i >= s.size())
                break;
            int x = last;
            if (i < s.size())
                x += s[i];
            if (i < b.s.size())
                x += b.s[i];
            c.s.push_back(x%BASE);
            last = x / BASE;
        }
        return c;
    }
    //比较运算
    bool operator<(const bignumber &b) const
    {
        if (s.size() != b.s.size())
            return s.size() < b.s.size();
        else
        {
            for (int i = s.size() - 1; i >= 0; i--)
                if (s[i] != b.s[i])
                    return s[i] < b.s[i];
        }
        return false;//相等
    }
    bool operator>(const bignumber &b) const { return b < *this; }
    bool operator<=(const bignumber &b) const { return !(b < *this); }
    bool operator>=(const bignumber &b) const { return !(*this < b); }
    bool operator!=(const bignumber &b) const { return b<*this || *this>b; }
    bool operator==(const bignumber &b) const { return !(b<*this || *this>b); }

};

int main()
{
    bignumber num1,num2;
    while (cin >> num1 >> num2)
    {
        cout << num1 + num2 << endl;;
        if (num1 < num2)
            cout << "<" << endl;
        else if(num1 > num2)
            cout << ">" << endl;
        else
            cout << "==" << endl;
    }
    return 0;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值