将一个大词典分成列表中的小词典

时间:2019-07-20 05:45:52

标签: python python-3.x parallel-processing

让我们说我有一本具有1000个键值的字典

x = {1: 'a', 2: 'b', 3: 'c', 4: 'd', 5: 'e', 6: 'f', ....}

我想将其转换为

x = [{1: 'a', 2: 'b', 3: 'c', ...}, {10: 'z', 11: 'z', 12: 'z', ...}]

我想知道python是否具有内置功能。我的关注点也是在缩放上。让我们说我在字典上有100万个键值,然后希望通过列表中的1000个键值将其分隔开

3 个答案:

答案 0 :(得分:3)

有那么多的值,我会考虑使用生成器来生成块。这很大程度上取决于您要如何处理它们(您是否需要同时使用所有这些或一次处理一个块):

# create some dictionary
x = {i: 'z' + str(i) for i in range(1, 22+1)}

def get_chunks(x, size=10):
    out = {}
    for i, k in enumerate(x, 1):
        if i % size == 0:
            yield out
            out = {}
        out[k] = x[k]
    # last chunk:
    if out:
        yield out

for chunk in get_chunks(x):
    print(chunk)

打印:

{1: 'z1', 2: 'z2', 3: 'z3', 4: 'z4', 5: 'z5', 6: 'z6', 7: 'z7', 8: 'z8', 9: 'z9'}
{10: 'z10', 11: 'z11', 12: 'z12', 13: 'z13', 14: 'z14', 15: 'z15', 16: 'z16', 17: 'z17', 18: 'z18', 19: 'z19'}
{20: 'z20', 21: 'z21', 22: 'z22'}

要将结果放入列表中:

print(list(get_chunks(x)))

答案 1 :(得分:3)

您可以使用itertools中的石斑鱼食谱(用所需的任何块大小替换10):

list(map(dict, zip(*[iter(x.items())] * 10)))

但是,如果您仅要遍历一系列下标,则不需要像问题所建议的那样昂贵地转换为列表,在这种情况下,您可以简单地遍历{{1 }}函数代替,这样既节省时间又节省内存:

map

答案 2 :(得分:1)

一个直截了当,极其丑陋的答案是这样的:

import itertools

def slice_it_up(d, n):
    return [{x for x in itertools.islice(d.items(), i, i+n)} for i in range(0, len(d), n)]

d = {'key1': 1, 'key2': 2, 'key3': 3, 'key4': 4, 'key5': 5}
dd = slice_it_up(d, 3)

print(dd)

此打印

[{('key2', 2), ('key1', 1), ('key3', 3)}, {('key5', 5), ('key4', 4)}]

但是,这绝对不是应该实际完成的事情。正如已经提到的第一个答案,您应该真正使用生成器来生成块。

由于您已经提到了某种并行处理(希望您不打算在那个阶段了解python的GIL是什么,所以请使用Google,看看是否会受到它的打击),至少您确实不必将itertools.islice结果(它是一个生成器)聚合到一个大的胖列表中,而直接将它们发送到处理中。