在Prolog中对List进行分区

时间:2015-03-30 22:00:15

标签: prolog

这是谓词:

partList(Len,L,R):-
    length(L,LL),
    length(R,RR),
    RR is LL/Len,
    append(R,L).

查询显示:

42 ?- partList(2,[t,t,t,f,f,t,f,f],R).
R = [[], [], [], [t, t, t, f, f, t, f, f]] .

但我想分区为

[[t,t],[t,f],[f,t],[f,f]]. 

我该如何解决这个问题?谢谢!

1 个答案:

答案 0 :(得分:2)

简单的方法是看问题是从列表的头部反复剥离前N个项目(直到列表用尽)。

partition( []      , []        ) .   % if the source list is exhausted, we're done.
partition( [X]     , [X]       ) .   % if the source list contains just one item, we're done.
partition( [X,Y|Z] , [[X,Y]|R] ) :-  % if the source list contains 2 or more items, we take the 1st two, and ...
  partition(Z,R)                     % - recursively partition the remainder.
  .                                  % Easy!.

使其通用化并不复杂。

首先,我们需要一种方法将列表分区为前缀,其中包含N个项目(如果列表不够长则更少)和后缀,包含剩下的东西(可能没什么):

take_prefix( _ , []     , []    , []     ) .  % if the source list is empty, both prefix and suffix are empty, regardless of the value of N.
take_prefix( 0 , [X|Xs] , []    , [X|Xs] ) .  % if N is 0, The prefix is the empty list and the suffix is the source list.
take_prefix( N , [X|Xs] , [X|P] , S      ) :- % otherwise, add the head to the prefix,
  N > 0 ,                                     % - assuming N > 0
  N1 is N-1 ,                                 % - decrement N
  take_prefix(N1,Xs,P,S)                      % - and recurse down.
  .                                           % Easy!

这是问题的症结所在。一旦你拥有了它,只需要反复(和递归)应用它,直到你到达空列表:

partition( _ , [] , []   ) .  % if the source list is empty, we're done.
partition( N , L , [P|R] ) :- % otherwise...
  take_prefix(N,L,P,S) ,      % - break it up into a prefix and a suffix,
  partition(N,S,R)            % - and recurse down on the suffix.
  .                           % Easy!