2

私はインターネットからこのことを読んでいました

オブジェクトの場合、機械はobject.__getattribute__変換b.xされますtype(b).__dict__['x'].__get__(b, type(b)).

実装は、インスタンス変数よりもデータ記述子に優先順位を 与え、非データ記述子よりもインスタンス変数に優先順位を与え、提供されている場合はgetattrに最低の優先順位を割り当てる優先順位チェーンを通じて機能します。

「インスタンス変数よりもデータ記述子を優先する」および「非データ記述子よりもインスタンス変数を優先する」の意味がわかりませんでした

誰かがこれが実際にどのように機能するかの例を教えてもらえますか?コードで何が優先されるかを知りたい

4

1 に答える 1

6

各オブジェクトには、その変数と関数を含む属性のディクショナリがあります。これらの辞書を参照してください。

If an instance’s dictionary has an entry with the same name as a data descriptor,    
the data descriptor takes precedence. If an instance’s dictionary has an entry with
the same name as a non-data descriptor, the dictionary entry takes precedence.

これは彼らが話していたことです。

これを表示するには:

#data descriptor
class A(object):
   def __get__(self, obj, type):
       print "hello from get A"
   def __set__(self, obj, val):
       print "hello from set A"
#non data descriptor
class B(object):
   def __get__(self, obj, type):
       print "hello from get B"

class C(object):
   #our data descriptor
   a = A()
   #our non data descriptor
   b = B()

>>> c = C()
>>> c.a
hello from get A
>>> c.b
hello from get B
>>> c.a = 0
hello from set A
>>> c.a          #notice after reassignment, A.__get__ is still called
hello from set A
>>> c.b = 0     #instance variable with the same name as the non data-descriptor
>>> c.b         #notice how B.__get__ isn't called anymore
0

基本的には、__get____set__がオブジェクト (データ記述子) に対してユーザー定義されている場合、デフォルトのメソッドの代わりに呼び出されるということです。__get__オブジェクト(非データ記述子)に対してユーザーが定義した場合のみ、インスタンスはインスタンス変数を再割り当てできます。

g.x = 0x がデータ記述子の場合、x のユーザー定義メソッドが呼び出さ__set__れ、x がインスタンス変数または非データ記述子の場合、デフォルトの動作が呼び出されます。

データ記述子を使用すると、クラスは変数へのすべてのアクセスと変更を制御します。データ記述子型の変数へのすべてのアクセスは、 および を経由__get____set__ます。そのため、クラスが定義した方法で call と ca が変更されますc.a = 0A.__set__タイプ A ではないインスタンス変数 'c​​a' を作成する方法はありません。

データ記述子以外の場合、クラスはアクセスのみを制御するため、c.b = 0が呼び出されると、__set__が定義されていないため、新しいインスタンス変数が作成されます (デフォルトの動作)。変数の設定に関するユーザー定義の動作はないため、動作なしで同じ名前のインスタンス変数を作成できます__get__

彼らが話している優先順位は、2 つのダイナミクスです。データ記述子は常に__get__andを呼び出す__set__ため、インスタンス変数を同じ名前で作成することはできません。__get__非データ記述子は、同じ名前のインスタンス変数が作成されるまでのみ呼び出されます。

于 2013-02-10T09:55:52.597 に答える