Боюсь, вы не можете легко.В Python классы содержат только методы и статические атрибуты.Нестатические атрибуты обычно хранятся в атрибуте __dict__
объектов.Это означает, что за исключением особых случаев, вы не можете легко узнать, какие атрибуты были назначены в методе родительского класса, в методе дочернего класса или даже вне какого-либо метода.
Я могу только представить себе мета-класс, который бы использовал метод __init__
для хранения атрибутов, которые были изменены во время его вызова:
import collections
import functools
import inspect
class Meta_attr(type):
init_func = {}
attrs = collections.defaultdict(set)
def __new__(cls, name, bases, namespace, **kwds):
c = type.__new__(cls, name, bases, namespace, **kwds)
cls.init_func[c] = c.__init__
@functools.wraps(c.__init__)
def init(self, *args, **kwargs):
before = set(self.__dict__.keys())
cls.init_func[c](self, *args, **kwargs)
after = set(self.__dict__.keys())
cls.attrs[c].update(after.difference(before))
init.__signature__ = inspect.signature(c.__init__)
c.__init__ = init
return c
class Parent(object, metaclass=Meta_attr):
def __init__(self, id, name):
self.id = id
self.name = name
def print_values(self):
res = {}
for el in Meta_attr.attrs[Parent]:
res[el] = vars(self)[el]
return res
class Child(Parent):
def __init__(self, id, name, last_name, age):
Parent.__init__(self, id, name)
self.last_name = last_name
self.age = age
Это дает:
>>> c = Child(1,"a","b", 20)
>>> c.print_values()
{'id': 1, 'name': 'a'}
ВНИМАНИЕ : если атрибут установлен вне метода __init__
, он не будет зарегистрирован этим мета-классом ...