程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> 大數加法和乘法,大數加法乘法

大數加法和乘法,大數加法乘法

編輯:C++入門知識

大數加法和乘法,大數加法乘法


計算兩個小的整形數相加的,用自帶的+運算符就可以很容易的解決,但是對於兩個很大的數來講是會溢出的。用+運算符就無法完成了,當然你可以重載+運算符。

  其實對於兩個大整數相加,就是用到我們小學時學加法的方法-------豎式加法,一位一位的去相加,相加的和大於9只要進一位就OK了。

代碼如下:

#include <string.h>
#include <stdio.h>
const int N=100;
char s1[N],s2[N];  //保存輸入的兩個大整數
int bign1[N],bign2[N];  //把大整數轉換成整數的形式

//把字符數字逆序轉換成整數數字,
void char_num(char *s,int bin[]){
    int len=strlen (s);
    for (int i=len-1,k=0;i>=0;i--)
        bin[k++]=s[i]-'0';
}

//計算兩個大整數的和
void _fun (int bin1[],int bin2[]){
    int i,j;
    for (i=0,j=0;i<N;i++,j++){
        bin1[i] += bin2[j];
        if (bin1[i] > 9){
            bin1[i] %= 10;
            bin1[i+1]++;
        }
    }
}
void print (int bin[]){
    bool flag=false;
    for (int i=N;i>=0;i--){
        if (flag)
            printf ("%d",bin[i]);
        else if (bin[i]){  //輸出第一個非零的數。
            printf ("%d",bin[i]);
            flag=true;
        }
    }
    putchar ('\n');
}

///只能計算兩個正的大整數相加
int main(){
    while (scanf ("%s%s",s1,s2)!=EOF){
        memset (bign1,0,sizeof (bign1));
        memset (bign2,0,sizeof (bign2));
        char_num (s1,bign1);
        char_num (s2,bign2);
        _fun (bign1,bign2);
        print (bign1);
    }
    return 0;
}

現在考慮乘法,基本的思路都是一樣的。

   現用usigned ans1[200]和usigned ans2[200]來保存兩個乘數,用reault[400]來存放兩個乘數的乘積。需說明一下,兩個200位的數相乘,其積最大為400位的數。計算的過程和小學時的列豎式乘法基本相同,只不過編程方便把進位的步驟放在後面同一進行而已。

相以835x49為例進行說明:

1步:835x9    。5x9的得到45個1,3x9得到27個10,8x9得到72個100.由於不處理進位,所以結果為:

位數       3    2   1   0

-----0 0  0   72 27 45

接下來算4x5,得到20個10;故上述結果變為:

位數       3    2   1   0

-----0 0  0   72 47 45

再算4x3,得到12個100;故上述結果為:

位數       3    2   1   0

-----0 0  0   84 47 45

最後算4x8,得到32個1000;故上述結果為:

位數        3     2   1    0

-----0 0  32   84 47 45

自此,乘法已經算完了 。接下來處理進位的問題。

把realut[0]留下5,把4加到reault[1],得到51,把1留下,把5加到reault[2],得89.........

最後得到:

位數    4    3     2   1    0

----0    4    0     9    1    5

總結一個規律:一個數的第 i 位和另一個數的第 j 位相乘,一定是要累加到結果的第 i+j 位。(i ,j都是從0開始自右往左數)

代碼如下:

#include <stdio.h>
#include <string.h>
const int N=200;
int len1,len2;

void char_num (char *s,unsigned bin[]){
    int len=strlen (s);
    for (int i=len-1,k=0;i>=0;i--)
        bin[k++]=s[i]-'0';
}
void _fun (unsigned bin1[],unsigned bin2[],unsigned ans[]){

    for (int i=0;i<len1;i++){
        for (int j=0;j<len2;j++)
            ans[i+j] += bin1[i]*bin2[j];  //兩個數的  i j  位相乘 累加到結果的 i+j 位。
    }
}
void _carry (unsigned bin[]){
    int len=2*N;
    for (int i=0;i<len;i++){
        if (bin[i] > 9){
            bin[i+1] += bin[i] / 10;
            bin[i] %= 10;
        }
    }
}
void print (unsigned bin[]){
    bool flag=false;
    for (int i=N*2;i>=0;i--){
        if (flag)
            printf ("%d",bin[i]);
        else if (bin[i]){
            printf ("%d",bin[i]);
            flag=true;
        }
    }
    if (!flag)
        putchar ('0');  //和 0 相乘的情況。
    putchar ('\n');
}
int main (){
    
    unsigned ans1[N],ans2[N],reault[2*N+10];
    char s1[N],s2[N];

    while (scanf("%s%s",s1,s2)!=EOF){
        
        memset (ans1,0,sizeof (ans1));
        memset (ans2,0,sizeof (ans2));
        memset (reault,0,sizeof (reault));

        len1=strlen (s1),len2=strlen (s2);
        char_num (s1,ans1);
        char_num (s2,ans2);

        _fun (ans1,ans2,reault);
        _carry (reault);
        print (reault);
    }
    return 0;
}

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved