2016-10-11 35 views
3

我有一本字典Python的 - 转换成字典清单长度为基于价值

d = {1: 3, 5: 6, 10: 2} 

我想将它转换为持有字典的键列表。每个键应该重复多次与其相关联的值。

我写这个代码,没有工作:

d = {1: 3, 5: 6, 10: 2} 
l = [] 
for i in d: 
    for j in range(d[i]): 
     l.append(i) 
l.sort() 
print(l) 

输出:

[1, 1, 1, 5, 5, 5, 5, 5, 5, 10, 10] 

但我想这是一个列表解析。如何才能做到这一点?

回答

2

您可以使用列表做COM捏:

[i for i in d for j in range(d[i])] 

产量:

[1, 1, 1, 10, 10, 5, 5, 5, 5, 5, 5] 

您可以再次对其进行排序,让你在寻找名单。

+2

或者你可以在做列表理解之前对'd'进行排序。对于大型字典,这会更快,因为字典中的项目数量少于生成的列表数量。换句话说,'[我为我在排序(d)为j在范围内(d [i])]''。 –

1

一种方法是使用itertools.chain胶水子表一起

>>> list(itertools.chain(*[[k]*v for k, v in d.items()])) 
[1, 1, 1, 10, 10, 5, 5, 5, 5, 5, 5] 

或者,如果你正在处理一个非常大的字典,那么你可以避开与itertools.chain.from_iterableitertools.repeat

>>> list(itertools.chain.from_iterable(itertools.repeat(k, v) for k, v in d.items())) 
[1, 1, 1, 10, 10, 5, 5, 5, 5, 5, 5] 
构建子列表

使用使用两个循环的列表理解的超大字典的比较时间:

>>> d = {i: i for i in range(100)} 
>>> %timeit list(itertools.chain.from_iterable(itertools.repeat(k, v) for k, v in d.items())) 
10000 loops, best of 3: 55.6 µs per loop 
>>> %timeit [k for k, v in d.items() for _ in range(v)] 
10000 loops, best of 3: 119 µs per loop 

目前尚不清楚是否希望你的输出排序(你的示例代码不排序),但如果是这样简单d.items()预先分类

# same as previous examples, but we sort d.items() 
list(itertools.chain(*[[k]*v for k, v in sorted(d.items())])) 
1

[k for k,v in d.items() for _ in range(v)] ...我想...

如果你需要它有序,你可以做

[k for k,v in sorted(d.items()) for _ in range(v)]