如果两个列表完全相同(元素的顺序很重要),我想编写一个返回 true 的函数。
我是这样试的:
same([ ], [ ]).
same([H1|R1], [H2|R2]):-
H1 == H2,
same(R1, R2).
Run Code Online (Sandbox Code Playgroud)
当两个列表相同时它返回真,我也希望如果我有
?- same(X, [1, 2, 3]).
Run Code Online (Sandbox Code Playgroud)
我想要它回来
X = [1, 2, 3].
Run Code Online (Sandbox Code Playgroud)
但是这样输入就不行了。以下是我得到的一些示例输出:
?- same([1, 2], [1, 2]).
true.
?- same([2, 1], [1, 2]).
false.
?- same(X, [1, 2, 3]).
false.
?- same([1, 2, 3], [1, 2, X]).
false.
Run Code Online (Sandbox Code Playgroud)
如何解决?
问题在于您正在使用==/2
(检查两个项目是否实例化相同)而不是=/2
(检查两个项目是否统一或统一)。只需更改为统一:
same([], []).
same([H1|R1], [H2|R2]):-
H1 = H2,
same(R1, R2).
Run Code Online (Sandbox Code Playgroud)
然后这将具有您正在寻找的行为:
| ?- same(X, [1, 2, 3]).
X = [1,2,3] ? a
no
| ?- same([1, 2], [1, 2]).
(1 ms) yes
| ?- same([2, 1], [1, 2]).
no
| ?- same([1, 2, 3], [1, 2, X]).
X = 3
(1 ms) yes
| ?- same([A,B,C], L).
L = [A,B,C]
yes
% In this last example, A, B, and C are variables. So it says L is [A,B,C],
% whatever A, B, and C are.
Run Code Online (Sandbox Code Playgroud)
如果X == 3
在 Prolog 中查询,并且X
未绑定到 value 3
,或者只是未绑定,则会失败。如果X
未绑定并且您查询 ,X = 3
则 Prolog 将统一X
(绑定)与3
并成功。
有关=/2
和之间区别的更多信息==/2
,请参阅Prolog 中 == 和 = 之间的区别是什么?
您也可以使用maplist
一个漂亮的、紧凑的解决方案。maplist
对于遍历列表非常方便:
same(L1, L2) :- maplist(=, L1, L2).
Run Code Online (Sandbox Code Playgroud)
这里,=/2
出于与上述完全相同的原因,仍然使用统一 ( )。
same(L1, L2) :- L1 = L2.
Run Code Online (Sandbox Code Playgroud)
或等效地:
same(L, L). % Would unify L1 and L2 queried as same(L1, L2)
Run Code Online (Sandbox Code Playgroud)
如果列表相同,这将成功,或者将尝试通过依次统一每个元素来统一它们。
| ?- same([1,2,X], [1,2,3]). % Or just [1,2,X] = [1,2,3]
X = 3
yes
| ?- same([1,2,X], [1,2,3,4]). % Or just [1,2,X] = [1,2,3,4]
no
Run Code Online (Sandbox Code Playgroud)
先前更精细的方法被认为是列表处理中的练习以供说明。但是比较和/或统一列表的最简单和最正确的方法是L1 = L2
.
归档时间: |
|
查看次数: |
9737 次 |
最近记录: |