1. ホーム
  2. scripting

[解決済み] 辞書を繰り返しながら、辞書の項目を削除するには?

2022-03-14 13:11:33

質問

Pythonで辞書の反復処理中に辞書から項目を削除することは正当ですか?

例えば

for k, v in mydict.iteritems():
   if k == val:
     del mydict[k]

このアイデアは、反復処理されている辞書のサブセットである新しい辞書を作成する代わりに、特定の条件を満たさない要素を辞書から削除することです。

これは良い解決策なのでしょうか?もっとエレガントで効率的な方法はありますか?

どのように解決するのですか?

EDITです。

について Python3 (またはそれ以上)です。

>>> mydict
{'four': 4, 'three': 3, 'one': 1}

>>> for k in list(mydict.keys()):
...     if mydict[k] == 3:
...         del mydict[k]
...
>>> mydict
{'four': 4, 'one': 1}

残りの回答は Python2 では動作しません。 Python3 を発生させ RuntimeError .

RuntimeError: 反復中に辞書のサイズが変更されました。

このようなことが起こるのは mydict.keys() はリストではなくイテレータを返します。 コメントで指摘されているように、単純に mydict.keys() をリストに変換するには list(mydict.keys()) と入力すれば、動作するはずです。


について パイソン2 :

コンソールでの簡単なテストでは、反復処理中に辞書を変更することはできないことがわかります。

>>> mydict = {'one': 1, 'two': 2, 'three': 3, 'four': 4}
>>> for k, v in mydict.iteritems():
...    if k == 'two':
...        del mydict[k]
...
------------------------------------------------------------
Traceback (most recent call last):
  File "<ipython console>", line 1, in <module>
RuntimeError: dictionary changed size during iteration

delnan の回答にあるように、エントリを削除すると、イテレータが次のエントリに進もうとするときに問題が発生します。その代わりに keys() メソッドでキーのリストを取得し、それを使って作業します。

>>> for k in mydict.keys():
...    if k == 'two':
...        del mydict[k]
...
>>> mydict
{'four': 4, 'three': 3, 'one': 1}

アイテムの値に基づいて削除する必要がある場合は items() メソッドで代用できます。

>>> for k, v in mydict.items():
...     if v == 3:
...         del mydict[k]
...
>>> mydict
{'four': 4, 'one': 1}