嵌套列表中的替换(prolog)
/*如果列表Ys是用Y替换列表Xs中所有出现的X的结果,则替换(X,Y,Xs,Ys)为真 这就是我到目前为止所做的:嵌套列表中的替换(prolog),prolog,Prolog,/*如果列表Ys是用Y替换列表Xs中所有出现的X的结果,则替换(X,Y,Xs,Ys)为真 这就是我到目前为止所做的: subs(_,_,[],[]). subs(X,Y,[X|L1],[Y|L2]):- subs(X,Y,L1,L2). subs(X,Y,[H|L1],[H|L2]):- X\=H, not(H=[_|_]), subs(X,Y,L1,L2). subs(X,Y,[H|_],[L2]):- X\=H, H=[_|_], subs(X,Y,H,L2). 我的代码可以工作,只是它忽
subs(_,_,[],[]).
subs(X,Y,[X|L1],[Y|L2]):- subs(X,Y,L1,L2).
subs(X,Y,[H|L1],[H|L2]):- X\=H, not(H=[_|_]), subs(X,Y,L1,L2).
subs(X,Y,[H|_],[L2]):- X\=H, H=[_|_], subs(X,Y,H,L2).
我的代码可以工作,只是它忽略了嵌套列表后面的元素。例如:
?- subs(a,b,[a,[a,c],a],Z).
Z = [b, [b, c]] .
我应该向这个程序添加什么?问题是,一旦找到嵌套列表,您就会忘记该嵌套列表后面的内容。相反,在使用嵌套嵌套进行递归之后,只需像以前一样继续。因此,您应将最后一条修改如下:
subs(X,Y,[H|L1],[H2|L2]):- X\=H, H=[_|_], subs(X,Y,H,H2), subs(X, Y, L1, L2).
除此之外,还有两种方法可以改进代码:
!/0
)停止回溯。这样你就不必重复你自己了?- subs(a, b, [a, [a, [d, f, a]], a, b, a, [g]], Z).
Z = [b, [b, [d, f, b]], b, b, b, [g]].
下面是如何使用(…->…;…)编写它:
削减是丑陋的,它们隐藏了以下条款中隐含的否定。我发现使用(…->…;…)更好,这类似于函数式编程中的if-then-else。@starblue:是的,我隐约记得cut存在一些问题(直到最近我才重新对Prolog产生兴趣)。我将在不久的将来仔细阅读。谢谢你的提醒,我会投票给你的答案:)这是家庭作业:下次,请给它贴上这样的标签!
?- subs(a, b, [a, [a, [d, f, a]], a, b, a, [g]], Z).
Z = [b, [b, [d, f, b]], b, b, b, [g]].
subs(_, _, [], []).
subs(X, Y, [H1|T1], [H2|T2]) :-
(H1 == X ->
H2 = Y
; is_list(H1) ->
subs(X, Y, H1, H2),
subs(X, Y, T1, T2)
;
H1 = H2,
subs(X, Y, T1, T2)
).