我想从包含属性x
的类继承,然后通过覆盖setter使该属性在子类中是只读的。如果父类中的__init__
使用原始setter,则此方法无效。请考虑以下代码。
class Parent:
def __init__(self, x=1):
# I want the following line to use the setter defined in the Parent
# class, even when __init__ is called from Child using super.
self.x = x
# Other initialization of Parent goes here.
@property
def x(self):
return self._x
@x.setter
def x(self, value):
"""Check that x is non-negative."""
if value < 0:
raise ValueError("x must be non-negative.")
self._x = value
class Child(Parent):
def __init__(self):
super().__init__() # Need this for initialization.
@property
def y(self):
return self._y
@y.setter
def y(self, value):
"""x can only be written to implicitly by setting y."""
self._y = value
self._x = abs(value)
@property
def x(self):
return self._x
@x.setter
def x(self, value):
raise AttributeError("Illegal access to x")
如果我现在尝试实例化Child
,我会AttributeError: Illegal access to x
,因为当调用行self.x = x
时,会调用x
Child
的设置者x
Parent
的{{1}}。如何让它以Pythonic方式使用Parent
的setter?
要明确的是,当self.x = ...
方法出现Parent
时,应该始终使用x
中的Parent
设置器,以及self.x = ...
时} Child
方法中出现,应该始终使用x
中的Child
setter,从而引发异常。
答案 0 :(得分:1)
我设法通过交换
来解决问题self.x = x
<{1>}中的
Parent.__init__
我也可以摆脱
Parent.x.fset(self, x)
在@property
def x(self):
return self._x
中,如果不是Child
,我会使用@x.setter
。