我有以下关系:index(X,N,List)。
例如:
index(X,2,[a,b,c]).
X=b
index(b,N,[a,b,c]).
N=2
我不知道如何使我的关系与第二个例子一起工作。它说N没有很好地定义 这是我的代码(适用于第一个示例)。
index(X,1,[X|_]).
index(X,N,[_|Tail]) :- N > 1, N1 is N - 1 , index(X,N1,Tail).
答案 0 :(得分:0)
当Prolog尝试评估定义N
的递归子句中的目标N > 1
和N1 is N - 1
时,变量index/3
尚未实例化为数字类型。这会导致您报告的实例化错误。
我不知道如何直接解决你的问题,但我有两个建议。第一种是使用累加器,以便可以评估递归子句中的算术运算:
get(M,Xs,X) :- get(1,M,Xs,X).
get(N,N,[X|_],X).
get(N,M,[_|Xs],X) :-
L is N + 1,
get(L,M,Xs,X).
例如:
?- index(N,[a,b],X).
N = 1,
X = a ;
N = 2,
X = b ;
false.
另一种是使用自然数字类型,以便可以通过统一构建索引:
nat(0).
nat(s(N)) :- nat(N).
get(s(0),[X|_],X).
get(s(N),[_|Y],X) :- get(N,Y,X).
例如,
?- get(N,[a,b],X).
N = s(0),
X = a ;
N = s(s(0)),
X = b ;
false.
希望这很有帮助。也许更有知识的人会出现并提供更好的解决方案。
答案 1 :(得分:0)
有一个内置nth1/3
的SWI-Prolog可以满足您的需求:
?- nth1(N, [a, b, c], b).
N = 2 ;
false.
查看其源代码:
?- listing(nth1).
lists:nth1(A, C, D) :-
integer(A), !,
B is A+ -1,
nth0_det(B, C, D).
lists:nth1(A, B, C) :-
var(A), !,
nth_gen(B, C, 1, A).
true.
?- listing(nth0_det).
lists:nth0_det(0, [A|_], A) :- !.
lists:nth0_det(1, [_, A|_], A) :- !.
lists:nth0_det(2, [_, _, A|_], A) :- !.
lists:nth0_det(3, [_, _, _, A|_], A) :- !.
lists:nth0_det(4, [_, _, _, _, A|_], A) :- !.
lists:nth0_det(5, [_, _, _, _, _, A|_], A) :- !.
lists:nth0_det(A, [_, _, _, _, _, _|C], D) :-
B is A+ -6,
B>=0,
nth0_det(B, C, D).
true.
?- listing(nth_gen).
lists:nth_gen([A|_], A, B, B).
lists:nth_gen([_|B], C, A, E) :-
succ(A, D),
nth_gen(B, C, D, E).
true.