【问题标题】:Prolog - How does this permute function work?Prolog - 这个置换函数是如何工作的?
【发布时间】:2014-10-21 21:06:54
【问题描述】:

对于我的生活,我无法弄清楚这个置换函数是如何准确工作的。

perm(L, [H|T]) :-
    append(V, [H|U], L),
    append(V,U,W),
    perm(W,T).
perm([],[]).

在我看来,第一个 append 获取 L 的最后一个元素并将其与 H 统一。然后内部 perm 调用置换其他元素并将它们与 T 统一。我只是不确定第二个 append 函数的作用.我知道如果没有它,每次寻找新解决方案的尝试都会将列表大小减少 1,但我无法解释这种行为。

【问题讨论】:

  • 您是否尝试过使用跟踪? (运行:trace, perm([1,2,3],X) for ex)
  • 试着考虑关系而不是功能... [H|T]L的排列如果L[H|U] 附加到V 和...。而[][]的排列
  • 是的,很多次。这对我来说仍然很困惑。假设我输入 perm([1,2,3],X)。最后 3 条痕迹会告诉我: Exit: (8) perm([1], [1]) ?蠕变出口:(7) perm([1, 2], [2, 1]) ?蠕变出口:(6) perm([1, 2, 3], [3, 2, 1]) ?看起来像是神奇地为我创造了排列的cree。

标签: list prolog permutation


【解决方案1】:

在我看来,第一个 append 采用 L 的最后一个元素并将其与 H 统一。

不是最后一个元素; 一些元素。

append(V, [H|U], L) 可以读取L = V + [H] + U,对于某些列表VU,以及某些元素H。在选择元素H 之后,它将L 分解为H 之前的部分和H 之后的部分:

?- append(V, [H|U], [1,2,3]).
V = [],
H = 1,
U = [2, 3] ;
V = [1],
H = 2,
U = [3] ;
V = [1, 2],
H = 3,
U = [] ;
false.

然后可以读取下一个appendW = V + U,因此WL,但删除了一些元素H

(SWI-Prolog 有一个 select 谓词,它以更易读的方式做同样的事情:

perm(L, [H|T]) :-
    select(H, L, Rest),
    perm(Rest, T).
perm([], []).

但它也有一个permutation 谓词,所以为什么要麻烦;)

【讨论】:

  • 此外,当 either 参数被充分实例化时,SWI 的 permutation/2 谓词也会终止。示例:?- permutation(Ls, [a,b,c]). 在这种情况下上述版本不会终止。
  • github.com/SWI-Prolog/swipl-devel/blob/…。为什么它可以终止?技术不是微不足道的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-07-17
  • 2016-02-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多