【问题标题】:Splitting a list of lists into multiple lists by length of sub list按子列表的长度将列表列表拆分为多个列表
【发布时间】:2020-03-19 13:11:37
【问题描述】:

我有一个如下所示的排序列表:

tokens = [[46565], [44460], [73, 2062], [1616, 338], [9424, 24899], [1820, 11268], [43533, 5356], [9930, 1053], [260, 259, 1151], [83, 31840, 292, 3826]]

我想按子列表的长度将它分成不同的列表,如下所示:

a = [[46565], [44460]]
b = [[73, 2062], [1616, 338], [9424, 24899], [1820, 11268], [43533, 5356], [9930, 1053]]
c = [[260, 259, 1151]]
d = [[83, 31840, 292, 3826]]

如果不循环整个原始列表并检查每个子列表的长度,我在尝试执行此操作时遇到了一些麻烦。

我想也许我可以做点什么:

lengths = list(map(len,tokens))

for k, v in zip(lengths, tokens):
    <SOME CODE HERE>

有什么想法吗?

【问题讨论】:

标签: python list sorting sublist


【解决方案1】:

一种方法是sorteditertools.groupby

[list(v) for _ ,v in groupby(sorted(tokens, key=len), key=len)]

[[[46565], [44460]],
 [[73, 2062],
  [1616, 338],
  [9424, 24899],
  [1820, 11268],
  [43533, 5356],
  [9930, 1053]],
 [[260, 259, 1151]],
 [[83, 31840, 292, 3826]]]

【讨论】:

  • {k: list(v) for k, v in groupby(sorted(tokens, key=len), key=len)}
【解决方案2】:

这是尽可能高效的,而且非常简单:

tokens = [
    [46565], [44460], [73, 2062], [1616, 338], 
    [9424, 24899], [1820, 11268], [43533, 5356], 
    [9930, 1053], [260, 259, 1151], 
    [83, 31840, 292, 3826]
]
groups = {}
for sublist in tokens:
    groups.setdefault(len(sublist), []).append(sublist)

在此运行之后,groups 将成为一个字典,其中包含子列表长度的键和该长度的所有子列表的值,按照它们在 tokens 中找到的顺序。然后,您可以根据需要将这些条目分配给命名变量(a = groups[1] 等),但对于大多数工作流程,您最好直接使用 groups 字典,因为这概括了解决方案(如果有 0 -长度列表?15 项列表呢?)。

单行列表推导无法做到这一点,因为您需要对每个输入值进行不同的聚类。对于聚合(像这样),最好的解决方案几乎总是在输入数据上运行for 循环并在输出字典中创建或更新条目。

字典的.setdefault 方法对于这种模式也非常有用,因为它省去了在更新之前检查条目是否存在的麻烦。或者,您可以使用groups = collections.defaultdict(list),然后通过groups[len(sublist)].append(sublist) 进行更新。

【讨论】:

  • 太棒了!非常感谢
【解决方案3】:

这不是最好的方法,但大部分都遵循。

import string

alphabets = string.ascii_lowercase

tokens = [[46565], [44460], [73, 2062], [1616, 338], [9424, 24899], [1820, 11268], [43533, 5356], [9930, 1053], [260, 259, 1151], [83, 31840, 292, 3826]]

numbering = {(ord(k)-96):k for k in alphabets}
output = {k:[] for k in alphabets}


lengths = list(map(len,tokens))

for k, v in zip(lengths, tokens):
    output[numbering[k]].append(v)

print(output)

这是输出:

{'a': [[46565], [44460]], 'b': [[73, 2062], [1616, 338], [9424, 24899], [1820, 11268], [43533, 5356], [9930, 1053]], 'c': [[260, 259, 1151]], 'd': [[83, 31840, 292, 3826]], 'e': [], 'f': [], 'g': [], 'h': [], 'i': [], 'j': [], 'k': [], 'l': [], 'm': [], 'n': [], 'o': [], 'p': [], 'q': [], 'r': [], 's': [], 't': [], 'u': [], 'v': [], 'w': [], 'x': [], 'y': [], 'z': []}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-10-01
    • 1970-01-01
    • 2019-03-27
    • 2019-06-05
    • 2018-11-25
    • 2011-03-28
    • 1970-01-01
    • 2018-12-08
    相关资源
    最近更新 更多