このディレクトリの索引
http://pc12.2ch.net/test/read.cgi/tech/1269438098/641
#  このスレの住民の方には楽勝かもしれませんがお願いします 
#   
#  場合の数を計算するときに、いわゆる「nCr」というものを使うことがある。これは、順番を特に決めない場合、n個のものからr個のものを取り出す場合をいい、 
#  7C5 = 7! / (7-5)!5! 
#  である。nCrであれば 
#  nCr = n! / (n-r)!r!  (但し、0≦r≦n) 
#   
#  この数を計算したい。 
#  1. nとrを入力させる。 
#  2. n!を計算させる 
#  3. (n-r)!を計算させる 
#  4. r!を計算させる 
#  5. (2)/(3)/(4)を計算する  
#   
#  しかしn!と(n-r)!がかなりの部分まで重複することを利用すれば、かなり計算の手間を省くことができる 
#  1から5の手順まで守ったプログラムと手間を省いたプログラムをそれぞれ作成しなさい 
# 

nCr(N,R,X) :-
      階乗(N,U1),
      V is N - R,
      階乗(V,U2),
      階乗(R,U3),
      X is U1 // U2 // U3.

%%%%%%%%%%%%%%%%%%%%%%%%%%%
nCr(N,R,X) :-
      U is N - R + 1,
      階乗(U,N,K1),
      階乗(R,K2),
      X is K1 // K2 .

%%%%%%%%%%%%%%%%%%%%%%%%%%%%
階乗(M,N,1) :- M > N,!.
階乗(M,N,X) :-
      M2 is M + 1,
      階乗(M2,N,Y),
      X is M * Y.

階乗(0,1) :- !.
階乗(1,1) :- !.
階乗(N,X) :-
      N2 is N - 1,
      階乗(N2,Y),
      X is N * Y,
      asserta((階乗(N,X) :- (!))).

nCr :-
      催促付き整数入力('n : ',N),
      催促付き整数入力('r : ',R),
      nCr(N,R,X),
      write_formatted('nCr = %tC%t = %t\n',[N,R,X]).