在prolog中管理列表

时间:2011-11-21 21:42:30

标签: list prolog filtering

我是Prolog的新手,正在寻求一些帮助。我想要做的是基本上得到一个列表L,包含在给定列表中重复至少两次的元素L'

实施例 L'= [1,2,1,3,4,3,2] => L = [1,2,3]。

到目前为止,我能够计算每个连续变量的出现次数

% pack(L1,L2) :- the list L2 is obtained from the list L1 by packing
%    repeated occurrences of elements into separate sublists.
%    (list,list) (+,?)

pack([],[]).
pack([X|Xs],[Z|Zs]) :- transfer(X,Xs,Ys,Z), pack(Ys,Zs).

% transfer(X,Xs,Ys,Z) Ys is the list that remains from the list Xs
%    when all leading copies of X are removed and transfered to Z

transfer(X,[],[],[X]).
transfer(X,[Y|Ys],[Y|Ys],[X]) :- X \= Y.
transfer(X,[X|Xs],Ys,[X|Zs]) :- transfer(X,Xs,Ys,Zs).

% encode(L1,L2) :- the list L2 is obtained from the list L1 by run-length
%    encoding. Consecutive duplicates of elements are encoded as terms [N,E],
%    where N is the number of duplicates of the element E.
%    (list,list) (+,?)

encode(L1,L2) :- pack(L1,L), transform(L,L2).

transform([],[]).
transform([[X|Xs]|Ys],[[N,X]|Zs]) :- length([X|Xs],N), transform(Ys,Zs).

将返回以下的touples列表

?- encode([a,a,a,a,b,c,c,a,a,d,e,e,e,e],X).
X = [[4,a],[1,b],[2,c],[2,a],[1,d][4,e]]

但仍然存在构建列表的问题,该列表将包含至少重复两次的不同元素。

如果有人可以帮助我,或指出我的方向很棒。

提前致谢

2 个答案:

答案 0 :(得分:1)

an element E of list L should:
   be a member of list L',
   be a member of list L'' where L'' is list L' if we remove element E.

检查select/3member/2findall/3和/或setof/3

答案 1 :(得分:0)

你可以写一个程序:

% E it's the list of are elements from L that repeat at least twice
elements_that_repeat_at_least_twice(L, E) :-
  elements_that_repeat_at_least_twice(L, [], E).

elements_that_repeat_at_least_twice([H|Ls], Dupl, E) :-
  ...

在elements_that_repeat_at_least_twice中,添加的列表 Dupl 将使您验证的每个元素多次出现。使用[H | Ls]检查L的每个元素。 使用memberchk / 2来验证H是否在L中:那么它至少是重复的。如果它还没有在Dupl中,请添加到它,然后递归。记得编写递归基本案例(在空列表[]处停止。)

现在我看到你添加了一些代码:然后我完成了建议:

elements_that_repeat_at_least_twice([], Dupl, Dupl).
elements_that_repeat_at_least_twice([H|Ls], Dupl, E) :-
  (  memberchk(H, Ls)
  -> ( \+ memberchk(H, Dupl)
     -> Dupl1 = [H|Dupl]
     ;  Dupl1 = Dupl
     )
  ;  Dupl1 = Dupl
  ),
  elements_that_repeat_at_least_twice(Ls, Dupl1, E).

完成后,请记住反转重复列表。