2009-02-22 7 views
14

私は常にそれを閉じされずに開かれたが、私はちょうど私が次のコード行を入力すると、ファイルが閉じられますことを確認した場合、ファイルが漏れるだろうと想定していた:pythonはどのようにgc'edされたファイルを閉じますか?

>>> f = open('somefile.txt') 
>>> del f 

ただ、純粋な好奇心から、 これはどのように作動しますか?ファイルに__ del __メソッドが含まれていないことがわかりました。

答えて

19

CPythonでは、ファイルオブジェクトが割り当て解除されると、少なくともファイルは閉じられます。 CPythonソースのObjects/fileobject.cfile_dealloc関数を参照してください。 Deallocメソッドは、__del__に固有のいくつかの問題を除いて、Cタイプの場合は__del__のようなものです。

+1

明確にするために、__del__はガベージコレクション中に呼び出され、ファイルオブジェクトの参照がなくなった瞬間に発生するファイルオブジェクトのPythonのC実装で呼び出されます。 –

4

となります。 Pythonの2.5

、使用

from __future__ import with_statement 

(Pythonの2.6または3.xの場合は、何もしない)

with open("someFile", "rU") as aFile: 
    # process the file 
    pass 
# At this point, the file was closed by the with statement. 
# Bonus, it's also out of scope of the with statement, 
# and eligible for GC. 
+0

これも私が想定したものです。しかし、Python 2.5.1のOS Xでは、私が投稿したコード行によって、Pythonインタプリタはファイルを解放します(Activity Monitorで検証済み)。 –

+0

ファイルが収集されると、Pythonはそのファイルを閉じることになっています。私はこれがfileobject.cのどこで起こっているのか見てきましたが、そこにはありません。おそらく、私が次に見ているのはgc機構のどこかにあります。私はこの質問が好きです。 –

+0

私はfileobject.cでそれを逃したように見えます(Gallagher参照)。私は本当にCPythonの内部をよりよく理解していたがっています。 –

0

ベストの推測では、ファイルの種類がビルトインされているためというタイプですインタプリタ自身がガベージコレクションでファイルを閉じることを処理します。

また、Pythonインタプリタが終了した後でのみチェックし、すべての "リークされた"ファイルハンドルは閉じられます。

+0

「プリミティブ型」(Javaから受け取った)の私の理解は、Pythonにプリミティブがないので、ファイルをプリミティブとして残しません。 –

+1

私はHUAGHAGUAHが「ビルトインタイプ」と言っていたと思います。 :) –

2

Pythonは、ガベージコレクションに加えて参照カウントと確定的破壊を使用します。オブジェクトへの参照がなくなると、オブジェクトはすぐに解放されます。ファイルを解放すると、ファイルが閉じます。

これは、例とは異なります。 Javaには非決定論的なガベージコレクションしかない。これは、オブジェクトが解放されたときにあなたが知っていることを意味するので、ファイルを手動で閉じる必要があります。

参照カウントは完全ではありません。プログラムから到達できない循環参照を持つオブジェクトを持つことができます。そのため、Pythonは参照カウントに加えてガベージコレクションを持っています。

関連する問題