near(a1,b1). near(b1,c1). near(c1,d1). near(d1,e1). near(e1,f1).
near(f1,g1). near(a1,a2). near(a2,a3). near(a3,a4). near(a4,a5).
near(a5,a6). near(a6,a7). near(a7,a8). near(a8,a9). near(b1,b2).
near(b2,b3). near(b3,b4). near(b4,b5). near(b5,b6). near(b6,b7).
near(b7,b8). near(b8,b9). near(c4,d4). near(d1,e4). near(e4,f4).
near(f4,g4). near(g4,h4). near(g1,g2). near(g2,g3). near(g3,g4).
near(f4,f5). near(f5,f6). near(f6,f7). near(f7,f8). near(f8,f9).
near(a6,b6). near(b6,c6). near(a9,b9). near(b9,c9). near(c9,d9).
near(d9,f9). near(f9,g9). near(g9,h9). near(h9,i9).
path(X,X).
path(X,Y):-
near(X,Z), path(Z,Y),
write(X),
write('->'),
write(Z).
maze(X,Y):-findall(X,path(X,Y),Path_List),write(Path_List).
这是寻找迷宫的方式。
我想要像这样打印
Route1 [18] a1 -> b1 -> c1 -> d1 -> e1 -> f1 -> g1 -> g2 -> g3 -> g4 -> h4 -> h5 -> h6 -> h7 -> h8 -> h9 -> i9
并显示其他4条路线。
我认为使用剪切?或回溯。但我无法触及此代码..
答案 0 :(得分:0)
通常,写出回溯算法实际解决问题所需的中间步骤是非常无用的技术。 path / 2 second子句产生的大部分输出都是' noise'。
这也是导致trace / 0作为Prolog的主要调试工具的动机。跟踪带有附加信息,如嵌套级别,必不可少以了解输出。
然后我建议摆脱路径/ 2中的写入,添加一个参数'带回来'路径,并写一个服务谓词打印:
path(X,X, [X]).
path(X,Y, [X|Cs]):-
near(X,Z), path(Z,Y, Cs).
maze(X,Y):- forall(path(X,Y,Ps),writeln(Ps)).
?- maze(a1,i9).
[a1,b1,c1,d1,e4,f4,f5,f6,f7,f8,f9,g9,h9,i9]
[a1,b1,b2,b3,b4,b5,b6,b7,b8,b9,c9,d9,f9,g9,h9,i9]
[a1,a2,a3,a4,a5,a6,a7,a8,a9,b9,c9,d9,f9,g9,h9,i9]
[a1,a2,a3,a4,a5,a6,b6,b7,b8,b9,c9,d9,f9,g9,h9,i9]
true.
不是很吸引人,但肯定更有用。
请注意,路径/ 3(以及路径/ 2)将在循环存在的情况下永远循环 ...
使用pqGraphviz编辑,此代码段
maze_g(X,Y) :-
graph_window(maze_g(X,Y),[]).
maze_g(X,Y,G) :-
forall(path(X,Y,Ns),
(maplist(make_node(G),Ns,Ps)
,nodes_chain(Ps,Cs)
,make_edges(G,Cs))).
后跟?- maze_g(a1,i9).
,产量