List erlang:按元素位置拆分或筛选列表

List erlang:按元素位置拆分或筛选列表,list,erlang,List,Erlang,在Erlang中,根据元素位置将给定列表拆分为子列表的最正确(也是最快)的方法是什么?例如,我想从列表[1,2,3,14,5,16,7,8]到[1,14,7],[2,5,8],[3,16]中得到每n个元素的子列表?N可以有任何合理的值 列表中没有按位置过滤的功能,因此您必须使用拆分: 1> Sp = fun Sp(L,N,R) when length(L) =< N -> lists:reverse([L|R]); 1> Sp(L,N,R) ->

在Erlang中,根据元素位置将给定列表拆分为子列表的最正确(也是最快)的方法是什么?例如,我想从列表[1,2,3,14,5,16,7,8]到[1,14,7],[2,5,8],[3,16]中得到每n个元素的子列表?N可以有任何合理的值

列表中没有按位置过滤的功能,因此您必须使用拆分:

1> Sp = fun Sp(L,N,R) when length(L) =< N -> lists:reverse([L|R]);          
1> Sp(L,N,R) -> {L1,L2} = lists:split(N,L), Sp(L2,N,[L1|R]) end.            
#Fun<erl_eval.42.90072148>
2> Split= fun (L,N) when is_list(L), is_integer(N), N > 0 -> Sp(L,N,[]) end.
#Fun<erl_eval.12.90072148>
3> Split([1,2,3,4,5,6,7,8],3).                                              
[[1,2,3],[4,5,6],[7,8]]
4>
1>Sp=funsp(L,N,R)当长度(L)=列表时:反向([L|R]);
1> Sp(L,N,R)->{L1,L2}=列表:split(N,L),Sp(L2,N,[L1|R])end。
#乐趣
2> Split=fun(L,N)当is_list(L),is_integer(N),N>0->Sp(L,N,[])结束时。
#乐趣
3> 分裂([1,2,3,4,5,6,7,8],3)。
[[1,2,3],[4,5,6],[7,8]]
4>
[编辑]哦,它没有回答问题。如果您不介意子列表的顺序,可能还有另一种解决方案

1> L = [1,2,3,4,5,6,7,8].
[1,2,3,4,5,6,7,8]
2> N = 3.
3
3> [lists:reverse(Y) || Y <- lists:foldl(fun(X,[H|T]) -> T++[[X|H]] end , lists:duplicate(N,[]),L)].               
[[3,6],[1,4,7],[2,5,8]]
4> 
1>L=[1,2,3,4,5,6,7,8]。
[1,2,3,4,5,6,7,8]
2> N=3。
3.
3> [列表:反向(Y)| Y T++[X | H]]结束,列表:重复(N,[]),L)]。
[[3,6],[1,4,7],[2,5,8]]
4> 
下一个版本将恢复顺序:

1> F = fun(List,Chunk) -> {Si,L1} = lists:foldl(fun(X,{S,[H|T]}) -> {S+1,T++[[X|H]]} end , {0,lists:duplicate(Chunk,[])},List),
1> {L2,L3} = lists:split(Chunk - Si rem Chunk,L1),                              
1> [lists:reverse(Y) || Y <- L3 ++ L2] end.                                     
#Fun<erl_eval.12.90072148>
2> F(lists:seq(1,130),11).    
[[1,12,23,34,45,56,67,78,89,100,111,122],
 [2,13,24,35,46,57,68,79,90,101,112,123],
 [3,14,25,36,47,58,69,80,91,102,113,124],
 [4,15,26,37,48,59,70,81,92,103,114,125],
 [5,16,27,38,49,60,71,82,93,104,115,126],
 [6,17,28,39,50,61,72,83,94,105,116,127],
 [7,18,29,40,51,62,73,84,95,106,117,128],
 [8,19,30,41,52,63,74,85,96,107,118,129],
 [9,20,31,42,53,64,75,86,97,108,119,130],
 [10,21,32,43,54,65,76,87,98,109,120],
 [11,22,33,44,55,66,77,88,99,110,121]]
3>
1>F=fun(List,Chunk)->{Si,L1}=lists:foldl(fun(X,{S,[H | T]})->{S+1,T++[[X | H]]}end,{0,lists:duplicate(Chunk,[])},List),
1> {L2,L3}=lists:split(Chunk-Si-rem Chunk,L1),
1> [列表:反向(Y)| Y F(列表:序号(1130),11)。
[[1,12,23,34,45,56,67,78,89,100,111,122],
[2,13,24,35,46,57,68,79,90,101,112,123],
[3,14,25,36,47,58,69,80,91,102,113,124],
[4,15,26,37,48,59,70,81,92,103,114,125],
[5,16,27,38,49,60,71,82,93,104,115,126],
[6,17,28,39,50,61,72,83,94,105,116,127],
[7,18,29,40,51,62,73,84,95,106,117,128],
[8,19,30,41,52,63,74,85,96,107,118,129],
[9,20,31,42,53,64,75,86,97,108,119,130],
[10,21,32,43,54,65,76,87,98,109,120],
[11,22,33,44,55,66,77,88,99,110,121]]
3>
您真的需要最快的方法吗?每次我用最简单(最简单)的方法开始实施。只有当我意识到这是性能瓶颈时,我才开始优化它

所以,最天真的方式是:

split(List, ByElem) ->
  do_split(List, lists:duplicate(ByElem, []), []).

do_split([], RestGroups, Acc) ->
  Groups = lists:reverse(Acc) ++ RestGroups,
  [ lists:reverse(G) || G <- Groups ];

do_split([Elem | Rest], [Group | RestGroups], Acc) ->
  do_split(Rest, RestGroups, [[Elem | Group] | Acc]);

do_split(List, [], Acc) ->
  do_split(List, lists:reverse(Acc), []).
split(列表,ByElem)->
进行拆分(列表,列表:重复(ByElem,[]),[])。
是否拆分([],RestGroups,Acc)->
组=列表:反向(Acc)+恢复组,
[列表:反向(G)| | G
do|u split(Rest、RestGroups、[Elem|Group]| Acc]);
是否拆分(列表,[],Acc)->
进行拆分(列表,列表:反向(Acc),[])。

事实上,我认为这与代码的性能无关,我也看不到任何显著改进的方法。

我知道如何简单地拆分列表,但这里我需要创建一个包含n个元素的列表。即,每3个元素列表:3>拆分([1,2,3,4,5,6,7,8],3)。[[1,4,7],[2,5,8],[3,6]]@Darkkey,我给了你一个答案。