60

たとえば、タッチすることで互いにオーバーラップする次のミックスインがありますdispatch()

class FooMixin(object):
    def dispatch(self, *args, **kwargs):
        # perform check A
        ...
        return super(FooMixin, self).dispatch(*args, **kwargs)

class BarMixin(object):
    def dispatch(self, *args, **kwargs):
        # perform check B
        ...
        return super(FooMixin, self).dispatch(*args, **kwargs)

ビューで注文を確認したい場合は、A-> Bをチェックしてください。コードはMyView(FooMixin, BarMixin, View)またはMyView(BarMixin, FooMixin, View)ですか?

そして、なぜ私たちは常にViewミックスインの後にまたはそのサブクラスを置くのですか?(djangoのジェネリックビューのソースコードを読んでこれに気づきましたが、その背後にある理論的根拠があればわかりません)

4

1 に答える 1

97

MROは基本的に深さ優先、左から右です。詳細については、新しいスタイルのPythonクラスのメソッド解決順序(MRO)を参照してください。

チェックするクラスの__mro__属性を確認できますが、FooMixin最初に「チェックA」を実行する場合は、最初に行う必要があります。

class UltimateBase(object):
    def dispatch(self, *args, **kwargs):
        print 'base dispatch'

class FooMixin(object):
    def dispatch(self, *args, **kwargs):
        print 'perform check A'
        return super(FooMixin, self).dispatch(*args, **kwargs)

class BarMixin(object):
    def dispatch(self, *args, **kwargs):
        print 'perform check B'
        return super(BarMixin, self).dispatch(*args, **kwargs)

class FooBar(FooMixin, BarMixin, UltimateBase):
    pass

FooBar().dispatch()

プリント:

perform check A
perform check B
base dispatch

Viewミックスインのメソッドを非表示にすることなく、ミックスインになかった属性ルックアップを「キャッチ」するために、最後にする必要があります。あなたの質問のその部分、つまり「なぜそれがまったく追加されたのか」または「なぜ最後に追加されたのか」を理解しているのかわかりません。

于 2012-04-04T20:32:35.790 に答える