Prolog:创建包含偶数索引元素的列表

时间:2013-05-07 18:39:28

标签: prolog

基本上,我需要编写一个谓词even_elts(L,M),这样L就是一个新的列表,它只包含来自M的偶数索引元素(0th,2nd,4th,等)

add_tail([X],[],X).
add_tail([H|NewT],[H|T],X) :-
   add_tail(NewT,T,X).

even_elts(L,[]) :- L = [].
even_elts(L,M) :- even_elts2(L,M,1).
even_elts2(L,[H2|T2],Ct) :-
   Ct2 is Ct + 1,
   ((Ct2 mod 2) =:= 0, add_tail(L,L2,H2), even_elts2(L2,T2,Ct2); even_elts2(L,T2,Ct2)).
even_elts2(_,[],_) :- !.

如果M为空或包含1或2个元素,则此方法有效。但是,它只从M获得第一个偶数索引元素,而不是其余元素。任何指针

编辑:通过删除奇数索引元素而不是尝试创建新列表并复制数据,以不同方式解决问题。但是,如果有人能为我的原始代码找到解决方案,我很乐意看到。

3 个答案:

答案 0 :(得分:3)

你使这比现在复杂得多。您可以使用模式匹配来获取每个偶数元素,然后在第二个(输出)参数中收集它们。

% an empty list does not have even elements
even_elts([], []).
% for all other lists, skip the second element (_),
% add the first to the output, recurse
even_elts([X, _ | L], [X | R]) :-
    even_elts(L, R).

答案 1 :(得分:2)

使用累加器的另一种方法:

even_elts(L,M) :-
  even_elts(M,0,[],L).

even_elts([H|T],I,Acc,Ans) :-
  ( I mod 2 =:= 0, append(Acc,[H], AccNew)
  ; I mod 2 =:= 1, AccNew = Acc
  ),
  Inew is I + 1,
  even_elts(T,Inew,AccNew,Ans).

even_elts([],_,Acc,Acc).

?- even_elts(X,[1,2,3,4,5]).
X = [1, 3, 5] ;

答案 2 :(得分:0)

evens([A,B|C], [A|D]):- !, .....
evens(X, X).

就是你所需要的。填空。 :)