5

新しいスタイルのクラスと古いスタイルのクラスでオブジェクトの破棄が異なる動作をする理由を理解しようとしています。

class Wrapper():
    class Inner(object):
        def __del__(self):
            print 'Inner destructor'

    innerInstance = Inner()

    def __del__(self):
        print 'Wrapper destructor'

if __name__ == '__main__':
    x = Wrapper()

終了時に、これは次のように出力します。

Wrapper destructor
Inner destructor

ただし、新しいスタイルクラスとしてWrapperを使用すると、ラッパーデストラクタのみが呼び出され、出力は次のようになります。

Wrapper destructor

誰かが上記の動作を説明できますか?

4

1 に答える 1

4

Pythonデータモデルは明示的に次のように述べています。

__del__()インタプリタの終了時にまだ存在するオブジェクトに対してメソッドが呼び出されることは保証されていません。

この場合、Wrapperインタプリタが終了しても(クラスとインスタンス)オブジェクトが存在するため、オブジェクトがファイナライズされる保証はありません。また、Wrapper インスタンスがファイナライズされていることはわかりますが、Wrapper クラスがファイナライズされるという保証はありません(これがインスタンスを保持しているものですInner)。


ちなみに、このコードをJythonで実行する__del__と、どちらのオブジェクトに対しても呼び出されません(古いスタイルのクラスを使用しているか、新しいスタイルのクラスを使用しているかに関係なく)。驚いたことに、オブジェクトを明示的に削除しても(Jythonでは)機能しません(ただし、このコードは、古いスタイル/新しいスタイルに関係なく、CPythonで機能します)。

class Wrapper():
    class Inner(object):
        def __del__(self):
            print 'Inner destructor'

    innerInstance = Inner()

    def __del__(self):
        print 'Wrapper destructor'

if __name__ == '__main__':
    print "foo"
    x = Wrapper()
    print "bar"
    del x
    del Wrapper
于 2013-01-14T17:52:59.623 に答える