[Project Euler]加入歐拉 Problem 16

來源:互聯網
上載者:User

215 = 32768 and the sum of its digits is 3 + 2 + 7 + 6 + 8 = 26.

What is the sum of the digits of the number 21000?

計算 2 的 1000次方的所有數位和?

這個設計大數乘方問題,我自己寫了一個計算大數乘方的函數來計算。

先來說下如何計算大數乘方的問題吧,通用的思路就是採用數組來分段處理大數,分段表示大數。(使用鏈表的話,其實也會更簡單,更省空間的)

下面的演算法中,我採用的是“萬進位”,用數組來儲存資料。

原理如下:

先說計數方法:

十進位和其他進位都是用權和數字(好象這裡名詞不對,記不清楚了)來計數的:

比如

 2 的 26次方

num= 67108864

我們可以這樣來寫這個數:

6710 8864 

令arr[0] = 6710, arr[1] = 8864

那麼,arr數組看起來就象和67108864是一樣的

 

看到這裡你明白了吧?

我們可以分段表示一個非常大的數而不必考慮它的溢出,

而只用考慮段數是否大於一個數即可

舉個例子:

上邊,單段的最大值是9999,每段不溢出

那麼,num就不會溢出

 

再一個乘法.

 

我們老祖宗給我們留下的算盤,很妙,

它其實就是最基本的電腦之一

 

我們算乘方時,

只用乘以一個數:

這樣來列式子:

  123456790

                *2=

--------------

      246913580

 

即:

123              
456                   790

  *2=             *2=                   *2=

-----        
-----             ------            

246              
912                 (1)580(溢出)       第三段有溢出,加到上一段

-----      
-----             --------

246            
913                     580

 

呵呵,就這樣,打算盤一樣,進位.

 

上面就是一般通用的原理了。上面的每段都是以999為限,My Code是以9999為限。 分段處理每段數,溢出則進位。下面計算

 

這樣計算2的1000次方就輕而易舉了。 至於如何將最後數組裡的每段數字相加,這個就簡單了,每段進行轉換,單個字元相加。

歐拉項目第16題/*-----------------------** 計算大數乘方** 採用萬進位------------------------*/#include <stdio.h>#include <stdlib.h>#define N 1000// 計算大數乘方的函式宣告,x 的 y次方,返回整形數組void BMul(int arr[], int x, int y);int main(){    int arr[N] = {1};    BMul(arr, 4536, 144);    int i;    for(i = 0; i < N; i++)    {        if(arr[i] != 0)        printf("%d", arr[i]);    }    int sum = 0;    for(i= 0; i < N; i++)    {        if(arr[i] != 0)        {            char s[4];            memset(s, '\0', 4);            sprintf(s, "%d", arr[i]);            int j = 0;            for(j =0; j < 4; j++)            {                if(s[j] != '\0')                sum += s[j] - 48;            }        }    }    printf("\n");    printf("%d", sum);    return 0;}void BMul(int arr[N], int x, int y){    int position = 1; // position 指示 x的y次方佔用的段數    int yt; // yt 指數計數器    int at; // 佔用段數計數器    int incse; //記錄進位資訊    int tmp = 0;    for(yt = 0; yt < y; yt++)    {        incse = 0;        for(at = 0; at < position; at++)        {            tmp = arr[at];            arr[at] *= x; // 第at段乘以x            arr[at] += incse; // 加上來自第 at - 1段的進位            if(arr[at] > 9999) // 判斷是否溢出            {                if(at == position - 1) // 如果是首段溢出                {                    arr[position] = arr[at] / 10000;                    arr[at] = arr[at] % 10000;                    position ++;                    break;                }                else                {                    incse = arr[at] / 10000;                    arr[at] = arr[at] % 10000;                }            }            else // 此段不溢出            incse = 0;  // 如果不溢出一定要記得將incse 歸為0 否則隔空跳位        }    }    //將整形數組逆序    int i;    for(i = 0; i < N / 2; i++)    {        int tmp;        tmp = arr[i];        arr[i]= arr[N - 1 - i];        arr[N - 1 - i] = tmp;    }}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.