我已经在房间中定义了门列表:
class facts
door : (string Room1, string Room2).
skarb : (string Skarb, string Room).
class predicates
go : (string Room1, string Room2, string* R_list) nondeterm anyflow.
is_Member : (string Room, string* R_list) nondeterm .
write_list : (string* R_list) nondeterm .
clauses
door("a", "b").
door("b", "e").
door("b", "c").
door("d", "e").
door("c", "d").
door("e", "f").
door("g", "e").
door("g", "a").
door("h", "b").
door("h", "a").
door("h", "f").
door("i", "b").
door("i", "h").
door("i", "c").
door("i", "k").
skarb("bomba", "d").
和一些谓词:
go(Room, Room, R_list) :- stdio::write("\n\nJest droga:"), write_list(R_list), !.
go(Room1, Room2, R_list) :- door(Room1, X), not(is_Member(X, R_list)), go(X, Room2, [X | R_list]).
go(Room1, Room2, R_list) :- door(X, Room1), not(is_Member(X, R_list)), go(Room2, X, [X | R_list]).
is_Member(Room, [Room | _]) :- !. is_Member(Room, [_ | Tail]) :- is_Member(Room, Tail).
write_list([]) :- !.
write_list([Head | Tail]) :- stdio::write( Head), write_list(Tail).
我正在寻找从一个房间到另一个房间的方式:
run():-
stdio::write("\nDroga z a do f"),
R_list=["a"],
go("a", "f", R_list),
fail.
这个谓词起作用并返回:
Jest droga:feba
Jest droga:fedcba
哪个房间列表,我必须从a到f传递。 跑():- stdio :: write(“\ nDroga z f do a”), R_list = [ “F”], go(“f”,“a”,R_list), 失败。 但是这一个,什么也没有回报。正如您可能已经注意到它与前一种情况相反。
答案 0 :(得分:1)
这个问题有点像家庭作业。你应该适当地标记它。
door(A, B)
这是从A
到B
的有向边
您定义中的door(A, B)
也不暗示door(B, A)
事实上,f不会导致任何其他房间。这或多或少都是死路一条。
免责声明:我不确定是否有比我建议的方式更好的方法。
此外,我不确定path
是否正确写入,因为我现在无法测试它。
你可以像这样建立一个新规则:
reversible_door(A,B):- door(A,B).
reversible_door(A,B):- door(B,A).
但你还是要注意周期。您可以通过跟踪访问过的房间来避免周期。
path(A,B,_):- reversible_door(A,B).
path(A,B,Nodes):- reversible_door(A,X),
not(member(X,Nodes)),
path(X,B,[A|Nodes]).
当然,这也假设没有自我边缘,例如door(A, A).
如果已经隐含了,那就太好了。但如果你愿意的话,你也可以检查一下。
这与问题没有直接关系,但您可以检查一个房间是否有not(skarb("bomba",A))