下記のように組み合わせの数を求めるプログラムを作ったのですが 大きい数を入力すると値が求められないときがありました。 値が何より大きくなると求められないとかあるのでしょうか? #include <stdio.h> long fact2(int,int); main() { int n, m; long c; printf("input n m ="); scanf("%d %d",&n, &m); c = fact2(n,m) / fact2(m,m); printf("%dC%d = %d\n",n, m, c); } long fact2(int n,int m) { int i; long c=1; for(i=n; i>=n-m+1; i--) c*=i; return(c); }
組み合わせの数
組み合わせの数
Re:組み合わせの数
> 値が何より大きくなると求められないとかあるのでしょうか? nとmの値の内容によります。 > for(i=n; i>=n-m+1; i--) c*=i; nとmの値によっては、cがlong型で扱える範囲を超える(オーバーフロー)ことがあります。 計算の順序を工夫することで、オーバーフローする時期を遅らせることはできます。 それでも、nとmの値によっては、いつかはオーバーフローします。 似たような話を、最近どこかのスレッドで見かけたような記憶があります。
Re:組み合わせの数
long型の最大値はLONG_MAXですから、
#include <limits.h> #include <stdio.h> int main(void) { printf("%ld\n",LONG_MAX); return 0; }を実行したら、その環境のlong最大値がわかります。
Re:組み合わせの数
ちょっと暇だったんで、作ってみました。
nCr=n-1Cr-1+n-1Cr の公式を使って、再帰呼び出しにしてみました。
fact2が初心者さんの関数、factが私が作った関数です。
nCr=n-1Cr-1+n-1Cr の公式を使って、再帰呼び出しにしてみました。
fact2が初心者さんの関数、factが私が作った関数です。
#include <stdio.h> long fact(int,int); long fact2(int,int); int main(void) { int n, m; long c; printf("input n m ="); scanf("%d %d",&n, &m); c = fact(n,m); printf("fact :%dC%d = %ld\n",n, m, c); c = fact2(n,m) / fact2(m,m); printf("fact2:%dC%d = %ld\n",n, m, c); return 0; } long fact(int n,int r) { if(r==1) return n; if(r==n-1) return n; return(fact(n-1,r-1)+fact(n-1,r)); } long fact2(int n,int m) { int i; long c=1; for(i=n; i>=n-m+1; i--) c*=i; return(c); }