28.12. gc --- ガベージコレクタインターフェース

このモジュールは、循環ガベージコレクタの無効化・検出頻度の調整・デバッグオブションの設定などを行うインターフェースを提供します。また、検出した到達不能オブジェクトのうち、解放する事ができないオブジェクトを参照する事もできます。循環ガベージコレクタはPyhonの参照カウントを補うためのものなので、もしプログラム中で循環参照が発生しない事が明らかな場合には検出をする必要はありません。自動検出は、 gc.disable() で停止する事ができます。メモリリークをデバッグするときには、 gc.set_debug(gc.DEBUG_LEAK) とします。これは gc.DEBUG_SAVEALL を含んでいることに注意しましょう。ガベージとして検出されたオブジェクトは、インスペクション用に gc.garbage に保存されます。

gc モジュールは、以下の関数を提供しています:

gc.enable()

自動ガベージコレクションを有効にします。

gc.disable()

自動ガベージコレクションを無効にします。

gc.isenabled()

自動ガベージコレクションが有効なら真を返します。

gc.collect([generation])

引数を指定しない場合は、全ての検出を行います。オプションの引数 generation は、どの世代を検出するかを (0 から 2 までの) 整数値で指定します。無効な世代番号を指定した場合は ValueError が発生します。検出した到達不可オブジェクトの数を返します。

バージョン 2.5 で変更: オプションの引数 generation が追加されました.

バージョン 2.6 で変更: 幾つかの組み込み型のフリーリストは、最高(第二)世代のGC、あるいはフルGCが実行されるたびにクリアされます。幾つかの型(特に intfloat)では、実装によっては、フリーリスト内の全てのオブジェクトが解放されるとは限りません。

gc.set_debug(flags)

ガベージコレクションのデバッグフラグを設定します。デバッグ情報は sys.stderr に出力されます。デバッグフラグは、下の値の組み合わせを指定する事ができます。

gc.get_debug()

現在のデバッグフラグを返します。

gc.get_objects()

現在追跡しているオブジェクトのリストを返します。このリストには、戻り値のリスト自身は含まれていません。

バージョン 2.2 で追加.

gc.set_threshold(threshold0[, threshold1[, threshold2]])

ガベージコレクションの閾値(検出頻度)を指定します。 threshold0 を 0 にすると、検出は行われません。

GCは、オブジェクトを走査された回数に従って3世代に分類します。新しいオブジェクトは最も若い(0 世代)に分類されます。もし、そのオブジェクトがガベージコレクションで削除されなければ、次に古い世代に分類されます。もっとも古い世代は 2 世代で、この世代に属するオブジェクトは他の世代に移動しません。ガベージコレクタは、最後に検出を行ってから生成・削除したオブジェクトの数をカウントしており、この数によって検出を開始します。オブジェクトの生成数 - 削除数が threshold0 より大きくなると、検出を開始します。最初は 0 世代のオブジェクトのみが検査されます。 0 世代の検査が threshold1 回実行されると、 1 世代のオブジェクトの検査を行います。同様に、 1 世代が threshold2 回検査されると、 2 世代の検査を行います。

gc.get_count()

現在の検出数を、 (count0, count1, count2) のタプルで返します。

バージョン 2.5 で追加.

gc.get_threshold()

現在の検出閾値を、 (threshold0, threshold1, threshold2) のタプルで返します。

gc.get_referrers(*objs)

objsで指定したオブジェクトのいずれかを参照しているオブジェクトのリストを返します。この関数では、ガベージコレクションをサポートしているコンテナのみを返します。他のオブジェクトを参照していても、ガベージコレクションをサポートしていない拡張型は含まれません。

尚、戻り値のリストには、すでに参照されなくなっているが、循環参照の一部でまだガベージコレクションで回収されていないオブジェクトも含まれるので注意が必要です。有効なオブジェクトのみを取得する場合、 get_referrers() の前に collect() を呼び出してください。

get_referrers() から返されるオブジェクトは作りかけや利用できない状態である場合があるので、利用する際には注意が必要です。 get_referrers() をデバッグ以外の目的で利用するのは避けてください。

バージョン 2.2 で追加.

gc.get_referents(*objs)

引数で指定したオブジェクトのいずれかから参照されている、全てのオブジェクトのリストを返します。参照先のオブジェクトは、引数で指定したオブジェクトの Cレベルメソッド tp_traverse で取得し、全てのオブジェクトが直接到達可能な全てのオブジェクトを返すわけではありません。 tp_traverse はガベージコレクションをサポートするオブジェクトのみが実装しており、ここで取得できるオブジェクトは循環参照の一部となる可能性のあるオブジェクトのみです。従って、例えば整数オブジェクトが直接到達可能であっても、このオブジェクトは戻り値には含まれません。

バージョン 2.3 で追加.

gc.is_tracked(obj)

obj がGCに管理されていたら True を返し、それ以外の場合は False を返します。一般的なルールとして、アトミックな(訳注:他のオブジェクトを参照しないで単一で値を表す型。 int や str など)型のインスタンスは管理されず、それ以外の型 (コンテナ型、ユーザー定義型など) のインスタンスは管理されます。しかし、いくつかの型では専用の最適化を行い、シンプルなインスタンスの場合に GCのオーバーヘッドを減らしています。 (例: 全ての key と value がアトミック型の値である dict)

>>> gc.is_tracked(0)
False
>>> gc.is_tracked("a")
False
>>> gc.is_tracked([])
True
>>> gc.is_tracked({})
False
>>> gc.is_tracked({"a": 1})
False
>>> gc.is_tracked({"a": []})
True

バージョン 2.7 で追加.

以下の変数は読み込み専用です。(変更することはできますが、再バインドする事はできません。)

gc.garbage

到達不能であることが検出されたが、解放する事ができないオブジェクトのリスト(回収不能オブジェクト)。デフォルトでは、 __del__() メソッドを持つオブジェクトのみが格納されます。 [1] __del__() メソッドを持つオブジェクトが循環参照に含まれている場合、その循環参照全体と、循環参照からのみ到達する事ができるオブジェクトは回収不能となります。このような場合には、Pythonは安全に __del__() を呼び出す順番を決定する事ができないため、自動的に解放することはできません。もし安全な解放順序がわかるのであれば、 garbage リストを参照して循環参照を破壊する事ができます。循環参照を破壊した後でも、そのオブジェクトは garbage リストから参照されているため、解放されません。解放するためには、循環参照を破壊した後、 del gc.garbage[:] のように garbage からオブジェクトを削除する必要があります。一般的には __del__() を持つオブジェクトが循環参照の一部とはならないように配慮し、 garbage はそのような循環参照が発生していない事を確認するために利用する方が良いでしょう。

DEBUG_SAVEALL が設定されている場合、全ての到達不能オブジェクトは解放されずにこのリストに格納されます。

以下は set_debug() に指定することのできる定数です:

gc.DEBUG_STATS

検出中に統計情報を出力します。この情報は、検出頻度を最適化する際に有益です。

gc.DEBUG_COLLECTABLE

見つかった回収可能オブジェクトの情報を出力します。

gc.DEBUG_UNCOLLECTABLE

見つかった回収不能オブジェクト(到達不能だが、ガベージコレクションで解放する事ができないオブジェクト)の情報を出力します。回収不能オブジェクトは、 garbage リストに追加されます。

gc.DEBUG_INSTANCES

DEBUG_COLLECTABLEDEBUG_UNCOLLECTABLE が設定されている場合、見つかったインスタンスオブジェクトの情報を出力します。

gc.DEBUG_OBJECTS

DEBUG_COLLECTABLEDEBUG_UNCOLLECTABLE が設定されている場合、見つかったインスタンスオブジェクト以外のオブジェクトの情報を出力します。

gc.DEBUG_SAVEALL

設定されている場合、全ての到達不能オブジェクトは解放されずに garbage に追加されます。これはプログラムのメモリリークをデバッグするときに便利です。

gc.DEBUG_LEAK

プログラムのメモリリークをデバッグするときに指定します。( DEBUG_COLLECTABLE | DEBUG_UNCOLLECTABLE | DEBUG_INSTANCES | DEBUG_OBJECTS | DEBUG_SAVEALL と同じ。)

脚注

[1]Python 2.2より前のバージョンでは、 __del__() メソッドを持つオブジェクトだけでなく、全ての到達不能オブジェクトが格納されていた。)