2016-11-11 250 views
4

创建列表我这样定义的一个字典(名单是一个整数列表):通过遍历字典

​​

现在,我想通过遍历该字典创建一个新的列表。最后,我希望它看起来像这样:

my_list = [list_name_list_item1, list_name_list_item2, 
       list_name_list_item3, another_list_name_another_list_item1] 

依此类推。

所以我的问题是:我怎么能意识到这一点?

我试图

for key in my_dictionary.keys(): 
    k = my_dictionary[key] 
    for value in my_dictionary.values(): 
     v = my_dictionary[value] 
     v = str(v) 
     my_list.append(k + '_' + v) 

但是,而不是所希望的输出I接收类型错误(unhashable类型: '列表')在本实施例中的第4行。

回答

5

您试图通过它的值获取字典项目,而您已经拥有了自己的价值。

my_dictionary = {'list_name' : [1,4,5], 'another_list_name': [6,7,8]} 

my_list = [k+"_"+str(v) for k,lv in my_dictionary.items() for v in lv] 

print(my_list) 

结果:

['another_list_name_6', 'another_list_name_7', 'another_list_name_8', 'list_name_1', 'list_name_4', 'list_name_5'] 

注意,因为在你的字典顺序不能保证,列表的顺序并不

使用列表理解这样做在一个线无论是。你可以根据键通过排序的项目固定的顺序:

my_list = [k+"_"+str(v) for k,lv in sorted(my_dictionary.items()) for v in lv] 
+0

非常感谢你的帮助!我对Python很新,所以我很感谢你的解释和解决方案! :) – Hisushi

0

你已经写在键的外环,然后用值的内环,并试图利用各值作为密钥,这是在该程序失败。只需使用字典的items方法循环键,值对,而不是:

["{}_{}".format(k,v) for k,v in d.items()] 

哎呀,无法解析所需的格式;我们要在内部列表中生成每个项目。不用担心...

d={1:[1,2,3],2:[4,5,6]} 
list(itertools.chain(*(
     ["{}_{}".format(k,i) for i in l] 
     for (k,l) in d.items()))) 

这有点复杂。我们再次从字典中获取键值对,然后在列表中创建一个内部循环,并将它们格式化为字符串。这会产生内部序列,所以我们使用链和*将其平坦化,最后将结果保存为一个列表。

编辑:结果Python 3.4.3在嵌套为生成器表达式时变得相当困惑;我不得不将内部变成一个列表,或者在格式化之前替换一些k和l的组合。

再次编辑:由于有人张贴在自删除的答案(这让我感到困惑),所以我太过于复杂。你可以在链式理解中做扁平化嵌套:

["{}_{}".format(k,v) for k,l in d.items() for v in l] 

该方法也由Jean-FrançoisFabre发布。

2

试试这个:

my_list = [] 
for key in my_dictionary: 
    for item in my_dictionary[key]: 
     my_list.append(str(key) + '_' + str(item)) 

希望这有助于。

0

你的直接问题是,dict().values()是一个生成器产生的字典值,而不是关键字,所以当你尝试在第4行进行查找时,它会失败(在这种情况下),因为字典中的值可以不能用作钥匙。在另一种情况下,比如{1:2, 3:4},它会失败,并且KeyError{1:2, 2:1}不会引发错误,但可能会导致令人困惑的行为。

至于您的实际问题,列表不会将任何名称归于数据,就像字典一样;他们只是存储索引。

def f() 
    a = 1 
    b = 2 
    c = 3 
    l = [a, b, c] 

    return l 

调用f()将返回[1, 2, 3],与ab任何概念,c被完全丧失。

如果你想只是在连接列表中你的字典,使得第一副本,然后调用.extend()上就足够了:

my_list = my_dictionary['list_name'][:] 
my_list.extend(my_dictionary['another_list_name']) 

如果你正在寻找保持列表的顺序'项目,同时仍然提到他们的名字,看看OrderedDict class in collections

+0

这不是值()是一个发电机;它的价值不是关键。在他的情况下,他们是列表,这是不可哈希,因此*不能*键,所以他得到一个类型错误,而不是一个关键错误。 –

+0

我措辞不佳;它应该说“是”而不是“回报”。 –

0

使用列表理解这样

d = {"test1":[1,2,3,],"test2":[4,5,6],"test3":[7,8,9]} 

new_list = [str(item[0])+'_'+str(v) for item in d.items() for v in item[1]] 

输出:

new_list: 
['test1_1', 
'test1_2', 
'test1_3', 
'test3_7', 
'test3_8', 
'test3_9', 
'test2_4', 
'test2_5', 
'test2_6'] 
0

让我们初始化我们的数据

In [1]: l0 = [1, 2, 3, 4] 

In [2]: l1 = [10, 20, 30, 40] 

In [3]: d = {'name0': l0, 'name1': l1} 

注意,在我的例子,从你的不同,名单内容不是字符串...不是列出异构容器吗?

也就是说,您不能简单地加入键和列表项,您最好使用内建的str(...)将这些值转换为字符串。

现在来解决你的问题......我用一个列表理解 与两个循环,外部循环首先,它是在字典中的项目(即键值对夫妇),内部循环次之,它在相应列表中的项目上。

In [4]: res = ['_'.join((str(k), str(i))) for k, l in d.items() for i in l] 

In [5]: print(res) 
['name0_1', 'name0_2', 'name0_3', 'name0_4', 'name1_10', 'name1_20', 'name1_30', 'name1_40'] 

In [6]: 

在你的情况下,使用str(k)+'_'+str(i)将被罚款为好,但对于具有固定'text'连接字符串当前成语是'text'.join(...)方法。请注意,.join需要一个SINGLE参数,一个可迭代的,因此在列表理解中,我使用join((..., ...)) 来收集单个参数中的联合。

+0

post scriptum - 正如其他人在他们的回答中所说的那样,你无法保证在外部循环中检索到的'k,l'项的任何特定顺序。 – gboffi