我无法弄清楚这出错的地方.请注意,我对Prolog很新,我确定我错过了一些东西 - 不知道那可能是什么.有人可以帮帮我吗?
谢谢,这是我的代码:
printSentence([]).
printSentence([W|[]]) :-
write(W),
write('.'),
nl.
printSentence([W|R]) :-
write(W),
write(' '),
printSentence(R).
transform([], Result).
transform([Word|Rest], Result) :-
replace(Word, Replacement),
append(Result, Replacement, NewResult),
transform(Rest, NewResult).
replace(my, your).
replace(i, you).
replace(you, me).
replace(am, are).
replace(Word, Word).
test :-
X = [you, are, my, only, hope],
transform(X, Result),
printSentence(Result).
Run Code Online (Sandbox Code Playgroud) 我是Prolog的新手,我在检查两个列表是否具有完全相同的元素时遇到了问题.元素可能具有不同的顺序.我有这个代码:
myremove(X, [X|T], T).
myremove(X, [H|T], [H|R]) :-
myremove(X, T, R).
same_elements([], []).
same_elements([H1|T1], L2) :-
myremove(H1, L2, Nl2),
same_elements(T1, Nl2).
Run Code Online (Sandbox Code Playgroud)
它的工作原理除外
?- same_elements([b,c,a], X).
Run Code Online (Sandbox Code Playgroud)
返回第一个结果后导致内存不足错误.那么我试图通过检查列表的长度是否相等并检查H1是L2的成员来缩小结果集:
mylength([], 0).
mylength([_|T], R) :-
mylength(T, Nr),
R is Nr+1.
mymember(X, [X|_]).
mymember(X, [_|T]) :-
mymember(X, T).
same_elements([], []).
same_elements([H1|T1], L2) :-
mylength([H1|T1], X),
mylength(L2, Y),
Y = X,
mymember(H1, L2),
myremove(H1, L2, Nl2),
same_elements(T1, Nl2).
Run Code Online (Sandbox Code Playgroud)
现在两个
?- same_elements([b,c,a], X).
?- same_elements(X, [b,c,a]).
Run Code Online (Sandbox Code Playgroud)
返回所有结果,但之后它们就会挂起.有一个更好的方法吗?
我有一个递归:
list_to_set([],[]).
list_to_set([A|X],[A|Y]):-
list_to_set(X,Y),
\+member(A,Y).
list_to_set([A|X],Y):-
list_to_set(X,Y),
member(A,Y).
Run Code Online (Sandbox Code Playgroud)
它将元素列表转换为集合.例如[1,1,2,3] - > [1,2,3].当我输入查询list_to_set([1,1,2,3],X).结果时X = (1,2,3),查找集合的复杂性就是O(n).现在我可以输入;替代品以确保没有其他可能的答案.显然没有,脚本会返回false.我的问题是:第二个脚本运行的计算复杂性是什么,为什么?
我有一个阶乘谓词fact(N,F),其中任N或F或两者是有界的数字。
例如,我可以拥有fact(3,F)或fact(N,6)。这是我的谓词,该谓词有效,但我不太了解如何做。我曾经使用过,trace但在理解上仍然有困难。
fact(0,1).
fact(N,F) :-
fact(N1,F1),
N is N1 + 1,
F is N * F1.
Run Code Online (Sandbox Code Playgroud) 我有这个例子:
descend(X,Y) :- child(X,Y).
descend(X,Y) :- child(X,Z), descend(Z,Y).
child(anne,bridget).
child(bridget,caroline).
child(caroline,donna).
Run Code Online (Sandbox Code Playgroud)
它工作得很好,我理解它.这是一个小练习的解决方案.我的解决方案是一样的,但改变了:
下降(X,Y): - 下降(X,Z),下降(Z,Y).
也就是说,改变child为descend第二descend规则.
如果我descend(X, Y).在第一个解决方案中查询,我获得:
?- descend(X, Y).
X = anne,
Y = bridget ;
X = bridget,
Y = caroline ;
X = caroline,
Y = donna ;
X = anne,
Y = caroline ;
X = anne,
Y = donna ;
X = bridget,
Y = donna ;
false.
Run Code Online (Sandbox Code Playgroud)
哪个是对的.但如果我用我的解决方案查询相同,我得到:
?- descend(X, Y).
X = anne,
Y …Run Code Online (Sandbox Code Playgroud) 假设我有一个prolog程序来连接这样的列表:
concat([],X,X).
concat([Head|Tail],X,[Head|R]) :- concat(Tail,X,R).
Run Code Online (Sandbox Code Playgroud)
我怎么知道哪些问题会返回有限数量的答案?例如,问
concat(X,Y,[1,2,3,4]).
Run Code Online (Sandbox Code Playgroud)
将返回有限解集:
X = [],
Y = [1, 2, 3, 4] ;
X = [1],
Y = [2, 3, 4] ;
X = [1, 2],
Y = [3, 4] ;
X = [1, 2, 3],
Y = [4] ;
X = [1, 2, 3, 4],
Y = [] ;
false.
Run Code Online (Sandbox Code Playgroud)
在提问时
concat(X,[2,3],Z).
Run Code Online (Sandbox Code Playgroud)
将返回一组无限的解决方案:
X = [],
Z = [1, 2, 3] ;
X = [_G24],
Z = [_G24, 1, 2, 3] ;
X = …Run Code Online (Sandbox Code Playgroud) 这是我简单的Prolog程序:
friend(X,Y):-
knows(X,Y).
friend(X,Z):-
friend(X,Y),
friend(Y,Z).
knows(brian,tom).
knows(tom,peter).
Run Code Online (Sandbox Code Playgroud)
如果我键入以下查询
friend(brian,peter).
Run Code Online (Sandbox Code Playgroud)
Prolog将提供以下输出:
?- friend(brian,peter).
true
Run Code Online (Sandbox Code Playgroud)
如果再输入一个分号,Prolog会说:
ERROR: Out of local stack
Run Code Online (Sandbox Code Playgroud)
我在这做错了什么?
所以
?- canCall(mary, Person).
Run Code Online (Sandbox Code Playgroud)
工作并终止,
?- canFind(mary, Person).
Run Code Online (Sandbox Code Playgroud)
也可以工作并终止。但是不知何故
?- canCall(mary, Person), canFind(mary, Person).
Run Code Online (Sandbox Code Playgroud)
不终止。可能是什么原因?
我试图通过将inorder列表转回BST来"反转"inorder遍历.
BST具有谓词形式node(Value,Left,Right)或者leaf,因此空树只是leaf一棵树,一个节点就是node(_,leaf,leaf).
给定谓词enumerate_bst(Elems,Bst),目标是匹配Bstinorder列表的所有可能性Elems.例如(注意setof/3):
?- setof(Bst,enumerate_bst([],Bst),Enum).
Enum = [leaf].
?- setof(Bst,enumerate_bst([1,2],Bst),Enum).
Enum = [
node(1, leaf, node(2, leaf, leaf)),
node(2, node(1, leaf, leaf), leaf)
].
?- setof(Bst,enumerate_bst([1,2,3],Bst),Enum).
Enum = [
node(1, leaf, node(2, leaf, node(3, leaf, leaf))),
node(1, leaf, node(3, node(2, leaf, leaf), leaf)),
node(2, node(1, leaf, leaf), node(3, leaf, leaf)),
node(3, node(1, leaf, node(2, leaf, leaf)), leaf),
node(3, node(2, node(1, leaf, leaf), leaf), leaf) …Run Code Online (Sandbox Code Playgroud) 我是一个新的Prolog开发人员,我试图让合并排序工作.查询
mergesort([2,1],T).
Run Code Online (Sandbox Code Playgroud)
会生产
T=[1,2];
T=[1,2];
T=[1,2];
...
Run Code Online (Sandbox Code Playgroud)
因此,虽然它似乎"正确"地对序列进行排序但它不会停止
另一方面,如果我有一个查询,如
mergesort([2,1],[2,1])
Run Code Online (Sandbox Code Playgroud)
它进入了一个无限循环.我想知道为什么会这样?
append([H|T],LISTB,[H|LISTC]):-
append(T,LISTB,LISTC).
split(LIST,L1,L2):-
length(LIST,LENGTH),
M is div(LENGTH,2),
append(L1,L2,LIST),
length(L1,L1LENGTH),
(L1LENGTH =:= M).
merge(A,[],A).
merge([],B,B).
merge([A|TA],[B|TB],[A|MERGED]) :-
A =< B,
merge(TA,[B|TB],MERGED).
merge([A|TA],[B|TB],[B|MERGED]) :-
B < A,
merge([A|TA],TB,MERGED).
mergesort([],[]).
mergesort([X],[X]).
mergesort(LIST,OLIST):-
split(LIST,L1,L2),
mergesort(L1,OLIST1),
mergesort(L2,OLIST2),
merge(OLIST1,OLIST2,OLIST).
Run Code Online (Sandbox Code Playgroud)