[英]Recursion with Max Integer
我正在編寫一個程序來計算數字的階乘。 我正在使用遞歸來解決此問題。 我遇到的問題是,一旦達到13號,由於INT的限制,它將拋出垃圾號。 我想做的是實現一種在錯誤發生時捕獲錯誤的方法(沒有硬性規定必須在x = 13處停止,而是通過輸出停止)。 這是我的嘗試:
#include <stdio.h>
int factorial( int n)
{
printf("Processing factorial( %d )\n", n);
if (n <= 1)
{
printf("Reached base case, returning...\n");
return 1;
}
else
{
int counter = n * factorial(n-1); //Recursion to multiply the lesser numbers
printf("Receiving results of factorial( %d ) = %d * %d! = %d\n", n, n, (n-1), counter);
if( counter/n != factorial(n-2) ) //my attempt at catching the wrong output
{
printf("This factorial is too high for this program ");
return factorial(n-1);
}
return counter;
printf("Doing recursion by calling factorial (%d -1)\n", n);
}
}
int main()
{
factorial(15);
}
問題在於該程序現在永遠不會終止。 它不斷循環並拋出隨機結果。
由於我無法回答自己的問題,因此我將使用以下解決方案進行編輯:
int jFactorial(int n)
{
if (n <= 1)
{
return 1;
}
else
{
int counter = n *jFactorial(n-1);
return counter;
}
}
void check( int n)
{
int x = 1;
for(x = 1; x < n+1; x++)
{
int result = jFactorial(x);
int prev = jFactorial(x-1);
if (((result/x) != prev) || result == 0 )
{
printf("The number %d makes function overflow \n", x);
}
else
{
printf("Result for %d is %d \n", x, result);
}
}
}
更好的方法是:
if (n <= 1) {
return 1;
} else {
int prev_fact = factorial(n - 1);
if (INT_MAX / prev_fact < n) { /* prev_fact * n will overflow */
printf("Result too big");
return prev_fact;
} else {
return prev_fact * n;
}
}
使用更准確的檢查(我希望)來確定乘法是否會溢出,並且不再添加對factorial
調用。
仔細觀察之后,發現我錯過了為C實現gmp的事實。這是C
的解決方案
我已經能夠在brew isntall gmp
Pro上運行它,使用自制軟件安裝gmp( brew isntall gmp
)
#include <gmp.h>
#include <stdio.h>
void factorial(mpz_t ret, unsigned n) {
if (n <= 1) {
mpz_set_ui(ret, 1);//Set the value to 1
} else {
//multiply (n-1)! with n
mpz_t ret_intermediate;
mpz_init (ret_intermediate);//Initializes to zero
factorial(ret_intermediate, n-1);
mpz_mul_ui(ret, ret_intermediate, n);
}
return;
}
int main(){
mpz_t result;
mpz_init (result);
factorial(result, 100);
char * str_result = mpz_get_str(NULL, 10, result);
printf("%s\n", str_result);
return 0;
}
快速瀏覽后,我找到了以下解決方案。 請注意,這是C ++解決方案。 我在下面簡要介紹了如何在ANSI C中執行相同的操作。
https://gmplib.org/這個c ++庫可以處理任意大的數字。
結帳https://gmplib.org/manual/C_002b_002b-Interface-General.html
整個代碼可能看起來像...。
#include <gmpxx.h>
#include <iostream>
mpz_class factorial(unsigned n) {
if (n <= 1) return mpz_class(1);
return mpz_class(n) * factorial(n-1);
}
int main(){
mpz_class result = factorial(100);
std::string str_result = result.get_str();
std::cout << str_result << std::endl;
return 0;
}
您可以使用ansi C實現相同的事情,其結構可以容納擴展的數字列表(使用鏈表或任何其他可擴展的arraylist容器),而您只需要實現三種方法即可……初始化,乘法和轉換串起來。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.