如何将 SWI-Prolog 中的 tuples_in/2 转换为 GNU Prolog 中的 fd_relation/2?
How to convert from tuples_in/2 in SWI-Prolog to fd_relation/2 in GNU Prolog?
以下示例代码使用 SWI-Prolog
% example from https://github.com/Anniepoo/swiplclpfd/blob/master/clpfd.adoc
:- use_module(library(clpfd)).
trains([[1,2,0,1], % from station, to station, departs at, arrives at
[2,3,4,5],
[2,3,0,1],
[3,4,5,6],
[3,4,2,3],
[3,4,8,9]]).
threepath(A, D, Ps) :-
Ps = [[A,B,_T0,T1],[B,C,T2,T3],[C,D,T4,_T5]],
T2 #> T1,
T4 #> T3,
trains(Ts),
tuples_in(Ps, Ts).
Gnu Prolog 有一个内置的 clp(fd) 求解器。语法大部分相同,但我们不需要包含库,tuples_in/2 谓词由 fd_relation/2 处理,这是一个 GNU Prolog 谓词。
trains([[1,2,0,1], % from station, to station, departs at, arrives at
[2,3,4,5],
[2,3,0,1],
[3,4,5,6],
[3,4,2,3],
[3,4,8,9]]).
threepath(A, D, Ps) :-
Ps = [[A,B,_T0,T1],[B,C,T2,T3],[C,D,T4,_T5]],
T2 #> T1,
T4 #> T3,
trains(Ts),
fd_relation(Ts, Ps).
这不会像写的那样工作,因为 fd_relation/2 需要一个变量列表。我得到一个 type_error(fd_variable),大概是因为 Ps 是一个变量列表的列表。
显示的例子应该产生这个
?- threepath(1, 4, Ps).
Ps = [[1, 2, 0, 1], [2, 3, 4, 5], [3, 4, 8, 9]].
如何在 GNU Prolog 中实现?
答案是使用maplist/2
% example from https://github.com/Anniepoo/swiplclpfd/blob/master/clpfd.adoc
trains([[1,2,0,1], % from station, to station, departs at, arrives at
[2,3,4,5],
[2,3,0,1],
[3,4,5,6],
[3,4,2,3],
[3,4,8,9]]).
threepath(A, D, Ps) :-
Ps = [[A,B,_T0,T1],[B,C,T2,T3],[C,D,T4,_T5]],
T2 #> T1,
T4 #> T3,
trains(Ts),
maplist(fd_relation(Ts), Ps).
这将产生预期的解决方案。
?- threepath(1, 4, Ps).
Ps = [[1,2,0,1],[2,3,4,5],[3,4,8,9]]
以下示例代码使用 SWI-Prolog
% example from https://github.com/Anniepoo/swiplclpfd/blob/master/clpfd.adoc
:- use_module(library(clpfd)).
trains([[1,2,0,1], % from station, to station, departs at, arrives at
[2,3,4,5],
[2,3,0,1],
[3,4,5,6],
[3,4,2,3],
[3,4,8,9]]).
threepath(A, D, Ps) :-
Ps = [[A,B,_T0,T1],[B,C,T2,T3],[C,D,T4,_T5]],
T2 #> T1,
T4 #> T3,
trains(Ts),
tuples_in(Ps, Ts).
Gnu Prolog 有一个内置的 clp(fd) 求解器。语法大部分相同,但我们不需要包含库,tuples_in/2 谓词由 fd_relation/2 处理,这是一个 GNU Prolog 谓词。
trains([[1,2,0,1], % from station, to station, departs at, arrives at
[2,3,4,5],
[2,3,0,1],
[3,4,5,6],
[3,4,2,3],
[3,4,8,9]]).
threepath(A, D, Ps) :-
Ps = [[A,B,_T0,T1],[B,C,T2,T3],[C,D,T4,_T5]],
T2 #> T1,
T4 #> T3,
trains(Ts),
fd_relation(Ts, Ps).
这不会像写的那样工作,因为 fd_relation/2 需要一个变量列表。我得到一个 type_error(fd_variable),大概是因为 Ps 是一个变量列表的列表。
显示的例子应该产生这个
?- threepath(1, 4, Ps).
Ps = [[1, 2, 0, 1], [2, 3, 4, 5], [3, 4, 8, 9]].
如何在 GNU Prolog 中实现?
答案是使用maplist/2
% example from https://github.com/Anniepoo/swiplclpfd/blob/master/clpfd.adoc
trains([[1,2,0,1], % from station, to station, departs at, arrives at
[2,3,4,5],
[2,3,0,1],
[3,4,5,6],
[3,4,2,3],
[3,4,8,9]]).
threepath(A, D, Ps) :-
Ps = [[A,B,_T0,T1],[B,C,T2,T3],[C,D,T4,_T5]],
T2 #> T1,
T4 #> T3,
trains(Ts),
maplist(fd_relation(Ts), Ps).
这将产生预期的解决方案。
?- threepath(1, 4, Ps).
Ps = [[1,2,0,1],[2,3,4,5],[3,4,8,9]]