2013-04-26 1 views
1

Prolog의 백 트랙킹을 통해 여러 가지 문제가 발생합니다. 기술적으로, 제공된 각 솔루션은 정확하다는 것을 이해하지만, 나에게는 유용하지 않습니다. 중복을 제거하는 방법이 있습니까? 프롤로그에서 중복을 방지하려면 어떻게해야합니까?

여기에 지금까지 내 코드입니다 :

flight(london, paris). 
flight(paris, amsterdam). 
flight(amsterdam, rome). 
flight(rome, paris). 
flight(rome, rio_de_janeiro). 
route_from(A,B) :- 
    flight(A,B). 
route_from(A,B) :- 
    flight(A,R), 
    route_from(R,B). 

예 쿼리는 다음과 같습니다

?- route_from(A, paris). 
A = london ; 
A = rome ; 
A = london ; 
A = london ; 
A = london ; 
A = london ; 
A = london ; 
A = london ; 
A = london ; 
etc. 

감사합니다.

답변

3

반복되는 솔루션을 반환하는 것보다 더 큰 문제가 있습니다. 그래프에 루프가 있으므로 프로그램이 그대로 루프됩니다. 이 도시로 이동하는 하나 개 이상의 방법이있는 경우 중복을 돌려 막을 수 없습니다, 지금

route_from(A,B) :- 
    route_from(A,B, []). 

route_from(A,B, _) :- 
    flight(A,B). 
route_from(A,B, Visited) :- 
    flight(A,R), 
    \+ member(A, Visited), 
    route_from(R,B, [A|Visited]). 

:

는 사용자가 방문한 도시 목록을 유지할 수 루프를 방지합니다. setof/3 + member/2을 사용하여 중복없이 모든 솔루션을 수집 할 수 있습니다.

route_from_without_duplicates(A,B):- 
    setof(A-B, route_from(A,B), Routes), 
    member(A-B, Routes). 
+0

고맙습니다. \ +의 목적은 무엇입니까? –

+0

부정 (실패한 것이 실패하면 성공); 이 예에서'A'는'Visited'의 멤버가 아니어야 함을 의미합니다. – gusbro