參考:階乘,遞迴函式,c語言常見資料型別範圍,算術溢位,高精度演算法
階乘:乙個正整數的階乘(factorial)是所有小於及等於該數的正整數的積,並且0的階乘為1。自然數n的階乘寫作n!。2023年,基斯頓·卡曼引進這個表示法。
亦即n!=1×2×3×...×n。階乘亦可以遞迴方式定義:0!=1,n!=(n-1)!×n。
遞迴函式:
乙個函式可以呼叫其他函式,而當它呼叫自己的時候,就稱其為遞迴(注意:遞迴函式必須要有終止條件)
c語言常見資料型別範圍:
signed 和 unsigned 分別對應 有符文 和 無符號
位元組數: 用sizeof()來求,例如 sizeof(int)==4
位數 即bit數 : 乙個位元組是8位,所以 sizeof(int)的位數是32位
取值範圍: 2進製下的最大取值 轉換成的 10進製數
例如:sizeof(int)的位數是32位,二進位制下除最高位符號位為0(表示正數),剩下31位取1,相加得+2147483647
注意:剩下31位下標是0-30,最高位是2^30。
算術溢位:算術溢位(arithmetic overflow)是指計算機進行算術運算產生的結果超出機器所能表示的範圍。
深入理解:
高精度演算法:計算機對於超大資料的一種模擬加,減,乘,除,乘方,階乘,開方等運算。---重點是模擬!
模擬誰呢?。。當然是模擬人啊,你想想人是怎麼計算加減乘除的。
入門詳解:
一種尋常的思路是直接遞迴:
#includeint fac(int但會出現乙個問題,在20!的時候,出現了負數?(算術溢位)n)int
main()
事實上,在第13!的時候,int就不夠儲存了,int的最大值是+2147483647
13!正確的答案是 6 227 020 800
而這段**的錯誤答案是:
一種簡單的解決方式是,是用取值範圍比int還大的資料型別來儲存
比如:long long ,double,long double etc....
例如 long long
但是,在21!的時候。。。
這算是基本滿足了題目的要求吧,但對於高階的資料範圍200也許你想到了用其他型別,比如最大的long double,4932位
但是。。mingw使用windows的c執行庫,裡面的printf不支援long double的輸出(你可以在linux環境下試試)
也許你試了試就會發現,看似4932位計算的如此之多,但long double的有效位只有18-19位,所以後面的4000多位,全部是0。
那怎麼辦呢??
用模擬的思想,
我們人是怎麼進行加減乘除運算的?。
相信聰明的你已經想到了幼兒園老師交的辦法
豎式計算:
指在計算過程中列一道豎式計算,使計算簡便。加法計算時相同數字對齊,若和超過10,則向前進1。
減法計算時相同數字對齊,若不夠減,則向前一位借1當10。
很簡單易懂的思想對吧,那怎麼實現呢?,如何把每一位數都存起來呢?
當然是用陣列啦。。。。
1 #include2這是定義了10000位,假如需要計算更大的數,可以改變n的值。const
int n=10000;//
定義乙個不可改變的常數n
3int
a[n];
4int
main()17}
18int k=n-1;19
while(a[k]==0) k--;//
刪除前導0
20for(int i=k;i>-1;i--) printf("%d"
,a[i]);
21 printf("
\n%d\n
",k+1);//
計算位數
22return0;
23 }
N的階乘 大數階乘
輸入n求n的階乘的準確值。input 輸入n 1 n 10000 output 輸出n的階乘 首先,要確定n的階乘的數字大概有多少位,這樣便於我們去選擇合適的演算法。階乘 當n 10000時,上式值為35660 已經向上取整 所以接受 include include include include ...
大數階乘65!
include include define n 200 void sub int left int right int result 實現兩個大數相乘的演算法 乘得的結果是反序的,這樣保證假如前面是0的話也可以保留 for i 0 i 2 n i 上面乘出來的結果的陣列可能有些位數是超過10的,所...
大數階乘演算法
大數階乘演算法 前幾天朋友問我乙個問題 10000的階乘怎麼算?當時我就有點懵,10000 這個數字太大了,無論用什麼資料型別儲存結果都會溢位。這可怎麼辦呢?一時間束手無策。然後被一頓鄙視。後來經朋友的提醒,才恍然大悟,終於知道怎麼實現了,原來是使用陣列來模擬數字,這樣無論結果數字有多大,只要陣列的...