2014-01-11 9 views
0

그래서 내 문제는 이런 소리 : 정수 번호의 목록을 주어, 순열에서 연속 된 값 사이의 차이의 절대 값이 <=3 인 속성을 가진 순열 목록을 생성하십시오. 예 : L=[2,7,5] ==>[[2,5,7], [7,5,2]].프롤로그에서 두 연속 요소 사이의 차이

지금까지 나는이

domains 
list=integer* 
lista=list* 

predicates 
perm(list,list) 
permutations(list,lista,integer) 
delete(integer,list,list) 
diff(list,integer) 

clauses 
perm([],[]). 
perm(Y,[A|X]):- 
    delete(A,Y,Y1), 
    perm(Y1,X). 
delete(A,[A|X],X). 
delete(A,[B|X],[B|Y]):- 
    delete(A,X,Y). 

perm_aux(L,X,3):- 
    perm(L,X), 
    diff(X,R), 
    abs(R)<=3. 

diff([],0). 
diff(???):- 
    ?????? 

permutations(L,R,3):- 
    findall(X,perm_aux(L,X,3),R). 

그래서 내가 그 차이를 만드는 부분에 붙어 썼다. 나는 2 개의 연속적인 요소마다 그것을 어떻게하는지 모른다. 도와주세요.

+0

. 쌍을 조합하여 사용하면 연속적이지 않은 숫자에 대해서도 좋은 차이를 얻을 수 있습니다. – user3043278

답변

1

차이점을 반환하지 않고 원하는 최대 차이를 부여하고 너무 큰 차이가 발생하거나 실패하면 즉시 실패하게합니다. 대신

그래서 diff(List, Max). 그리고 전화 :

다음
diff(X, 3). 

베이스의 경우는 다음과 같습니다 :

diff([], _). % Empty list always succeeds 
diff([_], _). % Single element list always succeeds 

을 그리고 당신의 재귀 경우는 것

diff(X,R), 
abs(R)<=3. % Note that this should be =< 

당신은이 것 모양 :

diff([X,Y|T], Max) :- 
    abs(X-Y) =< Max, 
    diff([Y|T], Max). 

당신은 연속적인 값의 최대 절대 차이를 제공하기 위해 diff을하려는 경우, 당신은 그것을 정의 할 수 있습니다 : 만 연속적인 숫자의 차이를 확인해야합니다

max_diff(X, Max) :- 
    max_diff(X, 0, Max). 
max_diff([], M, M). 
max_diff([_], M, M). 
max_diff([X,Y|T], MaxSoFar, Max) :- 
    Diff is abs(X-Y), 
    ( Diff > MaxSoFar 
    -> max_diff([Y|T], Diff, Max) 
    ; max_diff([Y|T], MaxSoFar, Max) 
    ). 
+0

나는 abs (Y-X)> Max,!, .....라고 쓰고 나는 다시 붙어있다. diff를 재귀 적으로 다시 호출하는 방법은 무엇입니까? – user3043278

+0

@ user3043278 성공을 위해 프로그램하기를 원하기 때문에'abs (X-Y) = lurker

+0

맞아요.하지만이 코드 조각은 처음 두 숫자 만 차이를 확인하는 두 개의 다른 목록을 보여줍니다. 다음 숫자는 차이가 없습니다. – user3043278