我正在尝试将列表拆分为另外两个列表。列表即使是偶数的元素和其他的列表奇怪。我一直在寻找iinternet的解决方案,但在我看来都像中文,我无法理解这个过程。所以这就是我一直在尝试的:
split(List,Odd,Even):-odd(List,Oddlist,Evenlist).
odd([H|T],Oddlist,Evenlist):-even(T,[H|Oddlist],Evenlist).
odd([],_,_).
even([H|T],Oddlist,Evenlist):-odd(T,Oddlist,[H|Evenlist]).
even([],_,_).
但我得到的唯一回报是像Oddlist = _7132946 Evenlist = _26997888。
我不知道我做错了什么。我会帮助你。谢谢!
答案 0 :(得分:3)
CapelliC的答案是完美的。只是解释一下:
如果你有这样的Prolog条款:
foo([H|T], [H|Z]) :- foo(T, Z).
然后你可以这样打电话:
?- foo([a,b,c], L). from: foo([H| T ], [H|Z]) with H = a, T = [b,c], L = [a|Z] call: foo([a|[b,c]], [a|Z])
然后导致递归调用:
call: foo([b,c], Z). from: foo([H| T ], [H|Z]) with H = b, T = [c], L = [b|Z] call: foo([b|[c]], [b|Z])
此时,您在开头制作的列表[a|Z]
现在为[a|[b|Z]]
,即[a,b|Z]
。
因此,您在作为第二个参数传递的变量中创建一个列表,并在列表的前面粘贴 H 。您给递归调用的列表的其余部分。您将继续在列表末尾添加元素,直到第一个列表为空列表。此时,您也将结束新列表:
foo([], []).
在您的示例中,有另一个谓词与第一个谓词相互递归:
foo([], [], []). foo([H|T], [H|F], B) :- bar(T, F, B). bar([], [], []). bar([H|T], F, [H|B]) :- foo(T, F, B).
当然,这将"解压缩"列表分为两个列表。
答案 1 :(得分:2)
你的想法必须改进......
首先,每种语言(不仅是Prolog)都需要符号一致地命名。所以我根据需要重命名了变量。
特定于Prolog,有一种特殊的方法可以使用'cons'列表,这些列表源自规则头上应用的模式匹配。这同样适用于基本情况:我们必须提供将在调用者中绑定变量的空列表。
整个代码:
split(List,Odd,Even):-odd(List,Odd,Even).
odd([H|T],[H|Odd],Even):-even(T,Odd,Even).
odd([],[],[]).
even([H|T],Odd,[H|Even]):-odd(T,Odd,Even).
even([],[],[]).
答案 2 :(得分:0)
我知道这篇文章现在已经很老了,但我想我也会添加解决方案,因此,如果有15分钟前像我这样的人,他们还有其他需要注意的地方。这种方式将列表向后建立,以创建最终列表。前三行是基本情况。
split_odd_even([], [], []).
split_odd_even([O], [O], []).
split_odd_even([O,E], [O], [E]).
split_odd_even([O,E|T], [O|OL], [E|EL]) :- split_odd_even(T, OL, EL).