【问题标题】:How do I change position of two elements in a list(PROLOG)如何更改列表中两个元素的位置(PROLOG)
【发布时间】:2017-06-13 01:01:37
【问题描述】:

谓词change_pos(E1, E2,Lin,Lout).

Lin 有任意数量的元素,我需要将所有出现的E1 更改为E2,反之亦然。并返回Lout

我正在考虑做这样的事情:

change(X, Y, [], []).
change(X, Y, [X|L], [Y,L1]):- change(X,Y,L,L1).
change(X, Y, [Z|L], [Z,L1]:- X \== Z, change(X,Y,L,L1).

但是这种方式不是刷列表的两个数字

【问题讨论】:

  • 我正在考虑做这样的事情:change(X, Y, [], [])。更改(X,Y,[X|L],[Y,L1]):- 更改(X,Y,L,L1)。 change(X, Y, [Z|L], [Z,L1]:- X \== Z, change(X,Y,L,L1)。但是这种方式不是刷列表的两个数字
  • @JessicaSimoes - 尝试将 [Y,L1] 更改为 [Y|L1][Z,L1] 更改为 [Z|L1]
  • 你真的很亲密!在第三个子句的 :- 之前,您还缺少一个 )
  • @Enigmativity 哦,我明白了。您将 OP 的评论代码复制到问题中。我通常会尝试让他们这样做。 :) 但是,鉴于该代码,我认为没有关闭的基础。
  • @false - 我已经投票决定重新开放。

标签: prolog


【解决方案1】:

我想,既然这是家庭作业,那就是学习列表处理和递归的练习。但在 Prolog 中,依次处理列表中每个术语的常用工具是maplist

% Rule for changing one element
change_element(X, Y, X, Y).
change_element(X, Y, Y, X).
change_element(X, Y, Z, Z) :- dif(X, Z), dif(Y, Z).

% Rule for changing a list
change(X, Y, L1, L2) :-
    maplist(change_element(X, Y), L1, L2).

产量:

?- change(a, b, [a,b,c,b,a], L).

L = [b, a, c, a, b] ? ;

no
?-


对于确定解决方案,您可以使用if_/3
change1(X, Y, A, B) :-
    if_(=(Y, A), B = X, A = B).
change2(X, Y, A, B) :-
    if_(=(X, A), B = Y, change1(X, Y, A, B)).

change(X, Y, L1, L2) :- maplist(change2(X, Y), L1, L2).

产量:

?- change(a, b, [a,b,c,b,a], L).

L = [b, a, c, a, b].

?-

【讨论】:

  • 你能确定这个吗?
  • ... 理想情况下是在一个单独的答案中,这已被关闭
  • 现在你可以再做一个答案了! (顺便说一句,= 可以用作运算符,change1/4 不需要作为单独的谓词
【解决方案2】:

你快到了。您的基本情况(空列表)和您的第二条规则(将X 替换为Y)基本上没问题(除了 cmets 中指出的细节)。但是,您错过了反之亦然的规则(将Y 替换为X)。在您的最后一条规则中,您可能希望确保 Z 不仅与 X 不同,而且与 Y 不同,否则 Z 将受到规则二或三的约束。

change(X, Y, [], []).
change(X, Y, [X|L], [Y|L1]) :-
   change(X,Y,L,L1).
change(X, Y, [Y|L], [X|L1]) :-   % <- vice versa case
   change(X,Y,L,L1).
change(X, Y, [Z|L], [Z|L1]) :-
      dif(X,Z),                  % <- neither X=Z
      dif(Y,Z),                  % <- nor vice versa
      change(X,Y,L,L1).

以下是一些示例查询。 [1,2,3,4]交换后的样子12反之亦然? p>

   ?- change(1,2,[1,2,3,4],L).
L = [2,1,3,4] ? ;
no

[2,1,3,4]在交换之前是什么样子12反之亦然?

   ?- change(1,2,L,[2,1,3,4]).
L = [1,2,3,4] ? ;
no

哪些元素被交换了 [1,2,3,4] 如果结果列表是 [2,1,3,4] ?

   ?- change(X,Y,[1,2,3,4],[2,1,3,4]).
X = 1,
Y = 2 ? ;
X = 2,
Y = 1 ? ;
no

【讨论】:

  • 所有这些; no ... 那么change(a,a,[a],[a]) 的两 (2) 个多余的答案呢?
  • @false:有趣的事实:在 Yap 中,查询 ?- change(a,a,[a],[a]). 确定性地成功。 :-)
  • repeat.一样吗?是吗?
  • @false:是的。有趣的是,我还没有注意到。如果我正确阅读 8.15.3.1,repeat/0 不应该终止,而是只要用户点击 ;,就会产生 true,对吧?
  • 确实如此。这是 1970 年代旧顶层的特征:如果没有变量替换,只需停止。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多