我注意到我不能以我想要的方式使用
这导致:
一个元类在调用
或者我完全错了?
FYI,我找到了一些相关主题,但并不完全是我要找的:
__init_subclass__
与Django模型类。似乎在父类的__init_subclass__
方法运行时,元类还没有完成创建子类。虽然我理解问题所在,并可以通过制作自定义元类来规避它,但我不理解的是为什么!在我的脑海中,我倾向于认为像__new__
这样的任何调用都应在像__init__
这样的任何调用之前完成。但这对于元类和__init_subclass__
并非如此,正如这里所示:class MetaMeta(type):
print('parsing MetaMeta')
def __call__(cls, *args, **kwargs):
print('entering MetaMeta.__call__')
instance = super().__call__(*args, **kwargs)
print('leaving MetaMeta.__call__')
return instance
class Meta(type, metaclass=MetaMeta):
print('parsing Meta')
def __init__(self, *args, **kwargs):
print(' entering Meta.__init__')
super().__init__(*args, **kwargs)
print(' leaving Meta.__init__')
def __new__(cls, *args, **kwargs):
print(f' entering Meta.__new__')
instance = super().__new__(cls, *args, **kwargs)
print(' leaving Meta.__new__')
return instance
class Parent(object, metaclass=Meta):
print('parsing Parent')
def __init_subclass__(cls, *args, **kwargs):
print(' entering Parent.__init_subclass__')
super().__init_subclass__(*args, **kwargs)
print(' leaving Parent.__init_subclass__')
class Child(Parent):
print('parsing Child')
这导致:
parsing MetaMeta
parsing Meta
parsing Parent
entering MetaMeta.__call__
entering Meta.__new__
leaving Meta.__new__
entering Meta.__init__
leaving Meta.__init__
leaving MetaMeta.__call__
parsing Child
entering MetaMeta.__call__
entering Meta.__new__
entering Parent.__init_subclass__
leaving Parent.__init_subclass__
leaving Meta.__new__
entering Meta.__init__
leaving Meta.__init__
leaving MetaMeta.__call__
一个元类在调用
__init_subclass__
后仍然可以在Meta.__new__
中设置类。这对我来说似乎很奇怪。为什么会这样,有没有办法在不使用自定义元类的情况下在Parent
中提供代码,使其在Meta.__new__
之后(可能在Meta.__init__
之前)完全运行?或者我完全错了?
FYI,我找到了一些相关主题,但并不完全是我要找的:
- python3元类的调用顺序
- 元类的__new__和__init__参数
- https://docs.python.org/3/reference/datamodel.html#customizing-class-creation
Meta.__new__
调用Parent.__init_subclass__
,而不是让MetaMeta.__call__
在完成__new__
后立即调用它?请注意,在提出这个问题后,我找到了一些关于这个主题的python.org讨论,但我认为它们没有澄清原因。