2016-04-24 53 views
2

__weakref__與弱引用有關。我得到了弱引用背後的全部想法,以及我可能在哪裏使用它們。我不明白的是在下面描述的唯一的事:爲什麼class .__ weakref__不是None,而instance .__ weakref__是None?

一個實例沒有屬性__weakref__本身,從類不同,因此實例繼承__weakref__從類,這意味着A.__weakref__應該是一樣A().__weakref__

>>> class A: pass 
... 
>>> A().__dict__   # Each instance starts out as an empty namespace 
{} 
>>> A.__weakref__ is None; 
False 
>>> A().__weakref__ is None #But this is True! 
True 

爲什麼A.__weakref__Noneinstance.__weakref__None雖然實例繼承類__weakref__

+0

*「,這意味着'甲.__ weakref__ '和'A().__ weakref__' *「一樣 - 顯然不是,所以你假設*」實例從類「*繼承'__weakref__'是不正確的。 'A .__ weakref__是A().__ weakref__'的計算結果爲'False'。 – jonrsharpe

回答

3

A class has a __weakref__descriptor object;這就像property或一種方法一樣;只有當你訪問對象的屬性時纔會自動綁定。弱引用的實際數據存儲在C結構中,這是Python用來表示內存中的類和實例的數據結構的一部分。

因此,實例不需要自己的__weakref__屬性。類描述符綁定到實例數據結構,然後C代碼只在正確的C結構中查找以檢索所需的信息。

訪問類的屬性,產生描述符對象本身。這不是None;它是描述符對象。在屬性上,綁定屬性會生成弱引用。沒有弱引用,意味着返回None

可以通過經由A.__dict__['__weakref__']訪問對象(到繞過正常type.__getattribute__()結合行爲),則直接調用上__get__重新創建描述符行爲:

>>> import weakref 
>>> class A(object): pass 
... 
>>> a = A() 
>>> A.__weakref__ 
<attribute '__weakref__' of 'A' objects> 
>>> descriptor = A.__dict__['__weakref__'] 
>>> descriptor.__get__(None, A) 
<attribute '__weakref__' of 'A' objects> 
>>> a = A() 
>>> a.__weakref__ is None 
True 
>>> descriptor.__get__(a) is None 
True 
>>> wr = weakref.ref(a) # add a weak reference 
>>> wr 
<weakref at 0x10bd86d68; to 'A' at 0x10bad3588> 
>>> a.__weakref__ 
<weakref at 0x10bd86d68; to 'A' at 0x10bad3588> 
>>> descriptor.__get__(a) 
<weakref at 0x10bd86d68; to 'A' at 0x10bad3588>