This solution causes some namespace pollution at the module level (three definitions rather than just one), but I find it easy to follow.
I'd like to be able to write something like this (lazy initialization), but unfortunately classes are not available in the body of their own definitions.
# wouldn't it be nice if we could do this?
class Foo(object):
instance = None
def __new__(cls):
if cls.instance is None:
cls.instance = object()
cls.instance.__class__ = Foo
return cls.instance
Since that isn't possible, we can break out the initialization and the static instance in
Eager Initialization:
import random
class FooMaker(object):
def __init__(self, *args):
self._count = random.random()
self._args = args
class Foo(object):
def __new__(self):
return foo_instance
foo_instance = FooMaker()
foo_instance.__class__ = Foo
Lazy initialization:
Eager Initialization:
import random
class FooMaker(object):
def __init__(self, *args):
self._count = random.random()
self._args = args
class Foo(object):
def __new__(self):
global foo_instance
if foo_instance is None:
foo_instance = FooMaker()
return foo_instance
foo_instance = None