19

5 つの辞書があり、それらのキーの結合が必要です。

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 を使用していますが、上記のコードが機能しなかったのはなぜでしょうか。

4

5 に答える 5

66

@chuck は、なぜ機能しないのかという質問に既に答えていると思いますが、これを行う簡単な方法は、unionメソッドが複数の引数を取ることができることを覚えておくことです。

allkey = set().union(*alldict)

ループやラムダなしで必要なことを行います。

于 2011-03-09T08:42:12.197 に答える
10

あなたのソリューションはリストの最初の 2 つの要素に対して機能しますが、その後dict1dict2セットに縮小され、そのセットは としてラムダに入れられますx。そのxため、メソッドはkeys()もうありません。

解決策は、リダクションを空のセット (たまたま共用体の中立要素) で初期化することにより、最初から x をセットにすることです。

初期化子で試してください:

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

ラムダを使用しない代替方法は次のとおりです。

allkey = reduce(set.union, map(set, map(dict.keys, alldict)))
于 2011-03-09T06:49:47.017 に答える
5

機能していないニューロンの簡単な戦略 (しゃれを意図したもの):

allkey = []

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

allkey = set(allkey)

集合内包表記を使用して、このコードをよりソーターな形式に変換できます。

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

このワンライナーは、従来の for ループと比較して非常に読みやすいです。ネストされたループをリストまたは集合内包表記に変換するための鍵は、内側のループ (ネストされたループでより速く変化するループ) を最後のインデックス (つまり ) として記述することです for key in dictio

于 2011-03-09T07:36:21.633 に答える
1
set().union(dict1.keys(),dict2.keys()...)

私はリストを試しましたが、うまくいかなかったので、誰かのためにここに載せました.

于 2013-07-16T08:00:42.473 に答える
1

もう 1 つ方法があります。

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

ある?)

于 2011-03-09T07:55:51.827 に答える