You could hold the instance you work with in a class attribute.
Whenever you want to reset the class, reassign a new instance to that attribute.
Here is how I would implement this approach:
class Foo:
instance = None # The single instance
def __init__(self, ...):
# Initialize the instance if Foo.instance does not exist, else fail
if type(self).instance is None:
# Initialization
type(self).instance = self
else:
raise RuntimeError("Only one instance of 'Foo' can exist at a time")
@classmethod
def reset(cls):
cls.instance = None # First clear Foo.instance so that __init__ does not fail
cls.instance = Foo(...) # Now the initialization can be called
Then, you can access the instance by simply referring to Foo.instance
.
I chose to have the reset
as a class method, thus decorated by @classmethod
.
With this decorator, the instance can be reset by calling Foo.reset()
, and the cls
parameter will be passed automatically to the method.
I prefer this approach (which is more or less a singleton pattern) over those you suggest, because in your situation, it appears logical to have a single instance of Foo
, since you want to reset it.
Therefore, I find it rather intuitive to "force" the use of a single instance.
On the other hand, you could have an instance outside of the class, and use a reset
instance method, defined:
def reset(self):
self.__init__()
But this might not work so well.
Say you want to set attributes outside of the __init__
method.
Calling __init__
will not reset those attributes.
Therefore, your instance will not be reset as expected.
Now if you hold a single instance and reassign it to a brand new one, you're certain that it will be absolutely clean.
Regarding what you call "creating a new instance", that's more or less what I chose, but the question is where to store it.
I think it makes sense to keep it warm in the class itself.
By the way, there shouldn't be any performance issue (as in "memory leak") with this solution, since only one Foo
instance is referenced at a time, and creating a new one will de-reference the previous one.