检查是否在派生 class 中重新分配了属性

Check if an attribute is reassigned in derived class

在 Python 2.7 中,我定义了以下示例 class:

class A:
    def __init__(self):
        self.a = 1
        self.b = 3

class B(A):
    def __init__(self):
        A.__init__(self)
        self.a = 1

obj_b = B()
print(vars(obj_b))

对象 obj_b 现在同时具有 ab。尽管 a 与 class A 具有相同的值,但已在 class B.
中重新分配 有什么方法可以判断 a 是否在 class B 中重新分配?

如果 a 是一个 class 属性,而不是一个实例属性,这个问题会更有意义。 A 的实例(可能是子 class)可以将 self.__class__.aA.a 进行比较。您可以将 self.aA().a 进行比较,但无法区分初始化期间所做的更改和其他任何时候所做的更改。

yeah, I see what you mean, thanks, so is there any way to check if such reassignment happened in class B's constructor?

回答评论里的一个问题,这个肯定可以的。这不是万无一失的,因为程序员可以不遗余力地欺骗您的系统,但他们必须故意这样做。

我们只需要把a变成property

class A:
    def __init__(self):
        self._a = 1
        self.was_a_changed = False

    @property
    def a(self):
        return self._a

    @a.setter
    def a(self, x):
        self._a = x
        self.was_a_changed = True

class B(A):
    def __init__(self):
        self.a = 1

class C(A):
    pass

obj_a = A()
obj_b = B()
obj_c = C()
print(obj_a.was_a_changed) # False
print(obj_b.was_a_changed) # True
print(obj_c.was_a_changed) # False

现在 a 不是一个实际值;它是由实际值 _a 支持的 属性。但是如果一个子类重新分配a,它会做一个注释,以便我们稍后检查它是否被触及。

如果有人想欺骗您的系统,他们总是可以直接分配给 self._a 而不是 self.a,但是如果 Python 分配给您不喜欢的私有对象,那将是不合常理的无论如何我都没有。