回答:
そのような機能はありません。これを行う最も簡単な方法は、dict内包表記を使用することです。
my_dictionary = {k: f(v) for k, v in my_dictionary.items()}
Python 2.7では、.iteritems()
代わりにメソッドを使用して.items()
メモリを節約します。dict内包構文はpython 2.7まで導入されませんでした。
リストにもそのようなメソッドがないことに注意してください。リスト内包表記またはmap()
関数を使用する必要があります。
そのため、map()
関数を使用して辞書を処理することもできます。
my_dictionary = dict(map(lambda kv: (kv[0], f(kv[1])), my_dictionary.iteritems()))
しかし、それは実際にはそれほど読みやすいものではありません。
dict(zip(a, map(f, a.values())))
少し短いですが、何をしているのかを考えなければなりません。そして、そうです。dictが変更されない場合、キーと値は同じ順序で繰り返されます。私はdictcompが何をしているかについてまったく考える必要がないので、それが正しい答えです。
my_dictionary.__getitem__
呼び出しを使用しているためです。
これらのツールは、この種の単純でありながら反復的なロジックに最適です。
http://toolz.readthedocs.org/en/latest/api.html#toolz.dicttoolz.valmap
あなたがなりたい場所を正しく取得します。
import toolz
def f(x):
return x+1
toolz.valmap(f, my_list)
これは、新しい辞書を作成するのではなく、インプレースで実行できます。これは、大規模な辞書(コピーが必要ない場合)に適している場合があります。
def mutate_dict(f,d):
for k, v in d.iteritems():
d[k] = f(v)
my_dictionary = {'a':1, 'b':2}
mutate_dict(lambda x: x+1, my_dictionary)
my_dictionary
含む結果:
{'a': 2, 'b': 3}
mapdict
を変更しmutate_values_with
たり、辞書を書き直したりできるようにする必要があります。:)
zip(d.keys(), d.values())
代わりに、より多くのバージョンで動作しますiteritems()
{k:f(v) for k,v in iter(d.items())}
起因してPEP-0469のアイテムにiteritemsを()と改名()とPEP-3113削除開梱パラメータタプルを、Pythonであなたが書く必要がありますから3.x マルタインピータース♦答えを次のように:
my_dictionary = dict(map(lambda item: (item[0], f(item[1])), my_dictionary.items()))
私の元の答えは要点を逃しましたが(defaultdictのファクトリーでAccessing keyのソリューションを使用してこの問題を解決しようとしたため)、現在の質問に対する実際のソリューションを提案するためにそれを作り直しました。
ここにあります:
class walkableDict(dict):
def walk(self, callback):
try:
for key in self:
self[key] = callback(self[key])
except TypeError:
return False
return True
使用法:
>>> d = walkableDict({ k1: v1, k2: v2 ... })
>>> d.walk(f)
アイデアは、元の辞書をサブクラス化して必要な機能を提供することです。つまり、すべての値に関数を「マッピング」します。
プラス点は、このディクショナリを使用しdict
て、コールバックで要求に応じてデータを変換しながら、元のデータをであるかのように格納できることです。
もちろん、クラスと関数に自由に名前を付けてください(この回答で選択した名前は、PHPのarray_walk()
関数に影響を受けています)。
注:どちらもtry
- except
ブロックやreturn
文は機能性のために必須です、彼らはそこにさらに模倣するためにPHPの振る舞いのですarray_walk
。
__missing__
渡されたファクトリメソッドが何らかの方法でフォールバックとしてorigin dictを使用しない限り、メソッドは既存のキーに対して呼び出されないため、これはOPの質問を解決できませんが、使用例の一部ではないため、私はこれを当面の問題に対して不十分な答えだと考えています。
Given a dictionary { k1: v1, k2: v2 ... } ...
。つまり、あなたはすでにdict
最初から..
{v1: f(v1), v2: f(v2), ...}
与えられたを取得する方法を[v1, v2, ...]
与え、口述は与えられませんでした。回答を編集して修正します。
次のようにラムダ内からインデックスを作成しないようにするには:
rval = dict(map(lambda kv : (kv[0], ' '.join(kv[1])), rval.iteritems()))
あなたも行うことができます:
rval = dict(map(lambda(k,v) : (k, ' '.join(v)), rval.iteritems()))
lambda(k,v)
ません。stackoverflow.com/questions/21892989/…を
ちょうどこのユースケースに遭遇しました。私はgensの回答を実装し、dictでもある値を処理するための再帰的なアプローチを追加しました。
def mutate_dict_in_place(f, d):
for k, v in d.iteritems():
if isinstance(v, dict):
mutate_dict_in_place(f, v)
else:
d[k] = f(v)
# Exemple handy usage
def utf8_everywhere(d):
mutate_dict_in_place((
lambda value:
value.decode('utf-8')
if isinstance(value, bytes)
else value
),
d
)
my_dict = {'a': b'byte1', 'b': {'c': b'byte2', 'd': b'byte3'}}
utf8_everywhere(my_dict)
print(my_dict)
これは、Python 2で文字列をバイトとしてエンコードするjsonまたはyamlファイルを処理するときに役立ちます。
dict((k, f(v)) for k, v in mydict.iteritems())
、すなわち、角括弧なしで、ジェネレータを介した中間リストの作成を防ぐでしょう。