user1592380
user1592380

Reputation: 36227

Inheritance and __dict__ in python 3

I'm reading through this blog post on OOP in python 3. In it there is:

class Door:
    colour = 'brown'

    def __init__(self, number, status):
        self.number = number
        self.status = status

    @classmethod
    def knock(cls):
        print("Knock!")

    def open(self):
        self.status = 'open'

    def close(self):
        self.status = 'closed'

class SecurityDoor:
    locked = True

    def __init__(self, number, status):
        self.door = Door(number, status)

    def open(self):
        if self.locked:
            return
        self.door.open()

    def __getattr__(self, attr):
        return getattr(self.door, attr)

When I do:

>>> sdoor = SecurityDoor(1, 'closed')
>>> sdoor.__dict__
{'door': <__main__.Door object at 0x0279A250>}

Why isn't "locked:True" in the attribute dictionary? After all, 'locked' is an attribute

Upvotes: 2

Views: 1115

Answers (1)

warvariuc
warvariuc

Reputation: 59594

Why isn't "locked:True" in the attribute dictionary?

Because you are inspecting instance dict, but locked is a class attribute. You can find it using self.__class__.__dict__.

If you need to see all attributes, including inherited and class attributes, use insect.getmembers() or the built-in dir function:

>>> import inspect
>>> class A(object):
...     b = 1
...     def __init__(self):
...         self.c = 1
...
>>> a = A()

>>> inspect.getmembers(a)
[('__class__', <class '__main__.A'>), ('__delattr__', <method-wrapper '__delattr__' of A object at 0x10d47f1d0>), ('__dict__', {'c': 1}), ('__doc__', None), ('__format__', <built-in method __format__ of A object at 0x10d47f1d0>), ('__getattribute__', <method-wrapper '__getattribute__' of A object at 0x10d47f1d0>), ('__hash__', <method-wrapper '__hash__' of A object at 0x10d47f1d0>), ('__init__', <bound method A.__init__ of <__main__.A object at 0x10d47f1d0>>), ('__module__', '__main__'), ('__new__', <built-in method __new__ of type object at 0x10d0d7280>), ('__reduce__', <built-in method __reduce__ of A object at 0x10d47f1d0>), ('__reduce_ex__', <built-in method __reduce_ex__ of A object at 0x10d47f1d0>), ('__repr__', <method-wrapper '__repr__' of A object at 0x10d47f1d0>), ('__setattr__', <method-wrapper '__setattr__' of A object at 0x10d47f1d0>), ('__sizeof__', <built-in method __sizeof__ of A object at 0x10d47f1d0>), ('__str__', <method-wrapper '__str__' of A object at 0x10d47f1d0>), ('__subclasshook__', <built-in method __subclasshook__ of type object at 0x7fc6b8638070>), ('__weakref__', None), ('b', 1), ('c', 1)]

>>> dir(a)
['__class__', '__delattr__', '__dict__', '__doc__', '__format__', '__getattribute__', '__hash__', '__init__', '__module__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', 'b', 'c']

>>> a.__class__.__dict__
dict_proxy({'__module__': '__main__', 'b': 1, '__dict__': <attribute '__dict__' of 'A' objects>, '__weakref__': <attribute '__weakref__' of 'A' objects>, '__doc__': None, '__init__': <function __init__ at 0x10d4791b8>})

Upvotes: 4

Related Questions