Python:defaultdictをdictに変換


93

defaultdictを変換するにはどうすればよいですか

number_to_letter
defaultdict(<class 'list'>, {'2': ['a'], '3': ['b'], '1': ['b', 'a']})

一般的な口述になるには?

{'2': ['a'], '3': ['b'], '1': ['b', 'a']}

11
dict(number_to_letter)
ティムピーターズ

2
@TimPetersは、これは実際にはわかりやすいタイトルで書かれた質問であるため(そして、検索で簡単に表示されるはずです)、将来の参照のために、より良い重複が見つからない場合の回答としてそれを置く価値があります。 。
ジョン・クレメンツ

この答えは役立つはずです:stackoverflow.com/a/3031915/1628832
karthikr 2013

1
@JonClements、良い点ですが、DSMはすでにそうしました-彼の答えが受け入れられることを願っています:-)
Tim Peters

2
あなたは、(恥知らずなプラグ)によって飛び出します- 10K上@TimPetersのおめでとうはところで...私はそれは長い間あなたを取らないだろう感じていたchat.stackoverflow.com/rooms/6/pythonいくつかのポイント:)で
ジョン・クレメンツを

回答:


124

あなたは単に呼び出すことができますdict

>>> a
defaultdict(<type 'list'>, {'1': ['b', 'a'], '3': ['b'], '2': ['a']})
>>> dict(a)
{'1': ['b', 'a'], '3': ['b'], '2': ['a']}

ただし、defaultdictdictあることに注意してください。

>>> isinstance(a, dict)
True

わずかに異なる動作と、中あなたが不足しているキーのアクセスを試みるときに-通常上げることになるKeyError-default_factory代わりに呼び出されます。

>>> a.default_factory
<type 'list'>

これprint aは、辞書のデータ側が表示される前に表示されるものです。

したがって、実際に新しいオブジェクトを作成せずに、より口述のような動作を取り戻すためのもう1つのトリックは、リセットすることdefault_factoryです。

>>> a.default_factory = None
>>> a[4].append(10)
Traceback (most recent call last):
  File "<ipython-input-6-0721ca19bee1>", line 1, in <module>
    a[4].append(10)
KeyError: 4

しかし、ほとんどの場合、これは問題の価値がありません。


Pythonでプログラミングを学び始めたところです。使い方について詳しく教えてdefault_factoryください。何が起こっているのか全く分かりません。ごめんなさい。
user2988464 2013

そして、「KeyError」とは何ですか?
user2988464 2013

5
@ user2988464:すでに使用していますdefault_factory-これはdefaultdictdefaultdict(int)またはのように、最初にを作成したときに渡した関数ですdefaultdict(list)a['3']たとえば、通常の辞書のように、辞書でキーを検索しようとすると、値を取得するか、KeyError例外が発生します(エラーなど、そのキーが見つからなかったことを通知します)。しかし中にdefaultdictは、代わりに呼び出すdefault_factoryための関数を作る(で「デフォルト」の新しいデフォルト値をdefaultdictあなたのため)。
DSM

3
Djangoの.itemsテンプレートプロパティはdefaultdictでは機能しないことに注意してください。これが、私がここにたどり着いた理由です。したがって、変換には1つの正当な理由があります
ベン

2
また、pickle(Pythonオブジェクトをファイルに保存するために)多くの状況でdefaultdictsを処理できないことに注意してください。
drevicko 2014

28

defaultdictが再帰的に定義されている場合、次に例を示します。

from collections import defaultdict
recurddict = lambda: defaultdict(recurddict)
data = recurddict()
data["hello"] = "world"
data["good"]["day"] = True

defaultdictをdictに戻すさらに別の簡単な方法は、jsonモジュールを使用することです。

import json
data = json.loads(json.dumps(data))

もちろん、defaultdictに含まれる値は、jsonでサポートされているデータ型に限定する必要がありますが、クラスや関数をdictに格納するつもりがなければ、問題にはなりません。


9
良い考えですが、私のデータはJSONにシリアル化されません:*(
Kasapo 2016

15

あなたも再帰的に変換するための再帰的なバージョンが必要な場合defaultdictdictは、次を試すことができます。

#! /usr/bin/env python3

from collections import defaultdict

def ddict():
    return defaultdict(ddict)

def ddict2dict(d):
    for k, v in d.items():
        if isinstance(v, dict):
            d[k] = ddict2dict(v)
    return dict(d)

myddict = ddict()

myddict["a"]["b"]["c"] = "value"

print(myddict)

mydict = ddict2dict(myddict)

print(mydict)

それはまさに私が必要としていたものです!残念ながら、私のdefaultdictには、カスタムエンコーダーなしではJSONシリアル化できないキーがいくつかあります(キーはタプルです-私の選択ではなく、私の問題です)
Kasapo 2016

1
良いもの。辞書の理解を使用することは、それが2層の深さしかない場合(つまりdefaultdict(lambda: defaultdict(int)))、簡潔です。 {k: dict(v) for k, v in foo.items()}
ggorlen19年
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.