How do I correctly clean up a Python object?

后端 未结 10 1131
北荒
北荒 2020-11-22 16:59
class Package:
    def __init__(self):
        self.files = []

    # ...

    def __del__(self):
        for file in self.files:
            os.unlink(file)
         


        
10条回答
  •  不知归路
    2020-11-22 17:31

    As an appendix to Clint's answer, you can simplify PackageResource using contextlib.contextmanager:

    @contextlib.contextmanager
    def packageResource():
        class Package:
            ...
        package = Package()
        yield package
        package.cleanup()
    

    Alternatively, though probably not as Pythonic, you can override Package.__new__:

    class Package(object):
        def __new__(cls, *args, **kwargs):
            @contextlib.contextmanager
            def packageResource():
                # adapt arguments if superclass takes some!
                package = super(Package, cls).__new__(cls)
                package.__init__(*args, **kwargs)
                yield package
                package.cleanup()
    
        def __init__(self, *args, **kwargs):
            ...
    

    and simply use with Package(...) as package.

    To get things shorter, name your cleanup function close and use contextlib.closing, in which case you can either use the unmodified Package class via with contextlib.closing(Package(...)) or override its __new__ to the simpler

    class Package(object):
        def __new__(cls, *args, **kwargs):
            package = super(Package, cls).__new__(cls)
            package.__init__(*args, **kwargs)
            return contextlib.closing(package)
    

    And this constructor is inherited, so you can simply inherit, e.g.

    class SubPackage(Package):
        def close(self):
            pass
    

提交回复
热议问题