2014-10-19 70 views
8

我有點困惑Python解釋器關閉時發生什麼事。 如果我寫一些代碼,這樣解釋器關閉時對象發生了什麼

class MyClass(object): 
    def __del__(self): 
     print "I'm going away" 

o = MyClass() 

並運行它,我會得到這個

I'm going away 

我的理解是,當翻譯關閉它會刪除所有引用創建的對象和這些如果指定對象將運行__del__()(因爲它們的引用計數爲0)。

我的困惑是因爲:

  1. 我不能夠找到說Python會在退出時清除所有引用的任何文件。
  2. 我很困惑,爲什麼當內存即將返回到操作系統並且聲明免費無論如何它正在清理對象。我猜想在複雜的系統中,刪除內存中即將釋放的對象的成本很高。
  3. 閱讀文檔__del__()我看到這個It is not guaranteed that __del__() methods are called for objects that still exist when the interpreter exits.它變得有點複雜了,他們是否說因爲某些循環依賴或它不能保證它不能保證運行?誰來決定?

所以我的問題是:

  1. 誰叫__del__在我上面的例子
  2. 爲什麼它不是guaranteed被調用時,我沒有參考週期
+1

不知道你在問什麼。你引用的文檔說'__del__'不能保證在解釋器退出時存在對象。不僅僅是具有參考週期的那些;沒有一個。一般來說,你不能認爲你的'__del__'方法會被調用。 – BrenBarn 2014-10-20 00:05:37

+0

我想我問了2個問題,首先,在上面的例子中,我叫__del__,其次是爲什麼當我沒有周期時,它不能保證。 – 2014-10-20 00:09:45

+2

文檔意味着可以或不可以調用解析器退出時存在的對象__del__。它看起來像你的情況,它被稱爲,但這基本上是運氣;你不能依靠它將被調用或不被調用的事實。至於你的第二個問題,我不知道技術上的原因,但事實就是這樣。文件很清楚,它就是這樣工作的。 – BrenBarn 2014-10-20 00:15:59

回答

2

我不沒有看到第一個問題的重點,但對於CPython 2.7.8,__del__PyInstanceObject.instance_dealloc調用,它被註冊爲tp_dealloc,它是calle d當調用Py_DECREF並且引用計數達到零時。所以,讓我們說解釋器調用它,而不是Python代碼。如果你問的是這個問題,希望你能改變被調用的方式或時間,我認爲這是不可能的。

至於爲什麼沒有保證,要做到這一點,你必須通過所有模塊在退出前刪除它們的變量,但如果__del__方法依賴於任何全局變量,沒有簡單的方法來保證安全的訂單他們被執行。我並不是說這是不可能的,就像參考週期一樣,我說這很複雜。

我想這是在某個時候討論過的,但社區或BDFL認爲這不值得冒險。我相信我在這幾年前看到過一些討論,但我現在找不到它。首先,從來沒有鼓勵使用__del__方法,如果您需要保證調用某個析構函數方法,那麼使用上下文管理器可能會更好。

+0

也不想爲競爭實施增加另一個嚴格的負擔。 – Veedrac 2014-10-21 01:45:33

+0

你是說這是一個假設,或者你知道是這樣嗎?毫無疑問,這是有道理的,但我不知道那是否被認爲是當時的情況。 – 2014-10-21 02:21:52

+0

這是一個猜測,是的。 – Veedrac 2014-10-21 02:29:35