19

辞書用のpython3.1ディープアップデート関数(親ディクショナリ内にある子ディクショナリを再帰的に更新する関数)が必要です。

しかし、将来的には、私の関数は辞書のように動作するがそうではないオブジェクトを処理する必要があると思います。isinstanceさらに、andの使用は避けたいと思いtypeます(ほとんどすべてのPythonistaのブログで読むことができるので、それらは悪いと見なされているため)。

しかし、ダックタイピングはPythonの哲学の一部なので、オブジェクトが辞書のようなものであるかどうかをどのように確認できますか?

ありがとう!

編集:答えてくれてありがとう。念のため、私がコーディングした関数は次の場所にあります:http: //blog.cafeaumiel.com/public/python/dict_deep_update.py

4

6 に答える 6

22

コレクションモジュールの(3.xの新機能)抽象基本クラス(ABC)を確認してください。

http://docs.python.org/3.1/library/collections.html

次のように、マッピングに対してisinstanceでチェックすることを検討します。

>>> import collections
>>> isinstance({},collections.Mapping)
True

次に、独自のdictのようなクラスを作成する場合は、collections.Mappingをそのベースの1つに作成します。

もう1つのルートは、ディクショナリ操作の例外をキャッチしようとしますが、あなたが話している再帰では、ディクショナリ、サブディクト、または他のディクテーションメンバーが何であったかを把握するよりも、最初に基本タイプをチェックしたいと思います。例外をスローするためにそこにありません。

追加する編集:dictではなくMapping ABCに対してチェックする利点は、dictをサブクラス化するかどうかに関係なく、同じテストがdictのようなクラスで機能するため、万が一の場合に備えて、より柔軟になります。

于 2009-08-14T14:08:58.143 に答える
3

を使用isinstanceしてください。問題はなく、再帰を必要とするコードで日常的に使用されています。

辞書のように、オブジェクトのクラスがから継承することを意味する場合はdictisinstanceも返しTrueます。

>>> class A(dict):
    pass

>>> a = A()
>>> isinstance(a, dict)
True
于 2009-08-14T13:43:29.797 に答える
1

辞書を再帰的に更新するには、「items」メソッドを呼び出して辞書を反復処理する必要があります。

だから私は提案します、あなたはただする:

try :
    for key, value in data.items() :
         # recursive call
except AttributeError :
    # handling the trouble
于 2009-08-14T19:47:54.947 に答える
1

ダックタイピングは、やりたいことを行う場所であり、オブジェクトが期待どおりに動作しない場合はフォールアウトに対処します。

何かがdictに似ているかどうかを確認し、そうである場合は更新しますか?オブジェクトのupdateメソッドを呼び出すだけで、そのようなメソッドがない場合に発生する例外を処理できます。

もちろん、他のことを完全に実行する更新メソッドを持つカスタムクラスオブジェクトを処理する場合、これはフラットになります-私はそれを処理する方法がよくわかりません。

于 2009-08-14T13:45:06.660 に答える
0

辞書のように動作するがdictからサブクラス化されていないカスタムクラスも処理する必要がある場合は、getattrを使用して必要な関数を取得できます。

# loop
# ... more code
someObject = getObject(..)
try:
    getattr(someObject, "update")("someValue")
except AttributeError:
    # Wasn't a type we can handle
于 2009-08-14T14:45:47.060 に答える
0

' __setitem__ 'マジックメソッドをチェックするのが好きです...これがfoo['bar']=bazの動作を可能にするものです。

if getattr(obj, '__setattr__'):
    obj[key] = val

これがPython2.7のドキュメントです

于 2014-06-26T18:40:42.357 に答える