2011-03-09 57 views
11

我有5個字典,我想要他們的鍵的聯合。python:來自多個字典的聯合鍵?

alldict = [dict1, dict2, dict3, dict4, dict5] 

我試圖

allkey = reduce(lambda x, y: set(x.keys()).union(y.keys()), alldict) 

,但它給了我一個錯誤

AttributeError: 'set' object has no attribute 'keys' 

上午我做錯了?我使用正常的forloop,但我想知道爲什麼上面的代碼不起作用。

回答

9

您的解決方案適用於列表中的前兩個元素,但隨後dict1dict2減少爲一個集合,並將該集合放入您的lambda中作爲x。所以現在x不再有方法keys()了。

解決的辦法是從一開始就通過初始化一個空集(這恰好是聯合的中性元素)的縮減來使x成爲集合。

與一個初始化嘗試:

allkey = reduce(lambda x, y: x.union(y.keys()), alldict, set()) 

沒有任何的lambda另一種方法是:

allkey = reduce(set.union, map(set, map(dict.keys, alldict))) 
+0

幾乎...嘗試set()作爲初始化程序 – itsadok 2011-03-09 06:52:35

+0

或者:allkey = reduce(set.union,(set(d.keys())for d in alldict))' – hughdbrown 2012-07-24 03:22:10

1

用於非功能性神經元(雙關語意)一個簡單的策略:

allkey = [] 

for dictio in alldict: 
    for key in dictio: 
     allkey.append(key) 

allkey = set(allkey) 

我們可以使用set comprehensions將此代碼轉換爲多種形式:

allkey = {key for dictio in alldict for key in dictio} 

與傳統的for循環相比,這種單行程仍然非常易讀。 將嵌套循環轉換爲列表或設置理解的關鍵是將最後一個索引(即for key in dictio)的內部循環(嵌套循環中變化較快的循環)寫入。

+0

如果這是一個列表理解,我會喜歡它。 – 2011-03-09 08:01:04

+0

@BjörnPollex你是對的,(集合)理解成功地與可讀性和簡潔性的功能替代品競爭。 – joaquin 2014-01-23 11:01:14

0

只是多了一個辦法,「造成什麼乾草:

a={}; [ a.update(b) for b in alldict ] and a.keys() 

或稍微更神祕

reduce(lambda a, b: a.update(b) or a, alldict, {}).keys() 

(我鬱悶,有沒有內置的功能等同於

def f(a,b): 
    r = {} 
    r.update(a) 
    r.update(b) 
    return r 

有沒有?)

+0

嘗試:'def f(a,b):return dict(a.items()+ b.items())' – hughdbrown 2012-07-24 03:24:11

30

我覺得@chuck已經回答了這個問題,爲什麼它不工作,而是一個更簡單的方法來做到這一點是需要記住的是,union方法可以採取多個參數:

allkey = set().union(*alldict) 

你想要做什麼,沒有任何環路或lambda。

0
set().union(dict1.keys(),dict2.keys()...) 

我試過這個列表,它沒有工作,所以只是把它放在這裏給任何人。