2014年3月15日土曜日

プロジェクトオイラー Problem 39 「整数の直角三角形」 †

Problem 39 「整数の直角三角形」 

辺の長さが {a,b,c} と整数の3つ組である直角三角形を考え, その周囲の長さを p とする. p = 120のときには3つの解が存在する:
{20,48,52}, {24,45,51}, {30,40,50}
p ≤ 1000 のとき解の数が最大になる p はいくつか?

http://odz.sakura.ne.jp/projecteuler/index.php?cmd=read&page=Problem%2039
原始ピタゴラス数とその倍数のリストを求めて個数をカウントするだけです。


gcd(0, B, B).
gcd(A, B, G) :- A > 0, R is B mod A, gcd(R, A, G).

stop(M,N):-M=<N.
stop(M,N):-
      Len is 2*M*(M+N),
      Len>1000.
calc_ok(M,N):-
      N<M,
      (M-N) mod 2=:=1,
      gcd(M,N,G),
      G=:=1.
roopD(M,N,Result):-
      between(1,1000,D),
      Result is 2*M*(M+N)*D,
      (Result>1000 -> !,fail;true).

roopN(M,Result):-
      between(1,M,N),
      (stop(M,N)->!,fail;true),
      calc_ok(M,N),

      roopD(M,N,Result).

roopM(Result):-
      between(2,35,M),
      (stop(M,1)->!,fail;true),
      roopN(M,Result).

count([],[Count,Len],[[Count,Len]]):-!.
count([Len|Rest],[Count,Len],Result):-
      !,
      Count1 is Count+1,
      count(Rest,[Count1,Len],Result).
count([Len1|Rest],[Count,Len],[[Count,Len]|Result]):-
      !,
      count(Rest,[1,Len1],Result).


main39:-
      findall(E,roopM(E),List),
      msort(List,[Top|List1]),
      count(List1,[1,Top],List2),
      msort(List2,List3),
      reverse(List3,[Ans|_]),
      write(Ans).

0 件のコメント:

コメントを投稿