We can show instance’s attribution with dir
function.
JavaScript
x
10
10
1
>>> class mytest():
2
test = 1
3
def __init__(self):
4
pass
5
>>> x=mytest()
6
>>> x.test
7
1
8
>>> dir(x)[-1]
9
'test'
10
Now create a class with metaclass method:
JavaScript
1
10
10
1
class Singleton(type):
2
_instances = {}
3
def __call__(cls, *args, **kwargs):
4
if cls not in cls._instances:
5
cls._instances[cls] = super(Singleton, cls).__call__(*args, **kwargs)
6
return cls._instances[cls]
7
8
class Cls(metaclass=Singleton):
9
pass
10
Show Cls’s _instances
attrubution:
JavaScript
1
3
1
Cls._instances
2
{<class '__main__.Cls'>: <__main__.Cls object at 0x7fb21270dc40>}
3
Why no string _instances
in dir(Cls)
?
JavaScript
1
11
11
1
>>> dir(Cls)
2
['__class__', '__delattr__', '__dict__', '__dir__', '__doc__',
3
'__eq__', '__format__', '__ge__', '__getattribute__', '__gt__',
4
'__hash__', '__init__', '__init_subclass__', '__le__', '__lt__',
5
'__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__',
6
'__repr__', '__setattr__', '__sizeof__', '__str__',
7
'__subclasshook__', '__weakref__']
8
>>> Cls.__dict__
9
mappingproxy({'__module__': '__main__', '__dict__': <attribute '__dict__' of 'Cls' objects>,
10
'__weakref__': <attribute '__weakref__' of 'Cls' objects>, '__doc__': None})
11
Advertisement
Answer
Because it’s stored on the metaclass.
JavaScript
1
5
1
>>> '_instances' in dir(Singleton)
2
True
3
>>> Singleton._instances
4
{<class '__main__.Cls'>: <__main__.Cls object at 0x7fb21270dc40>}
5
To be clear, this has nothing to do with the singleton aspect.