У меня есть большое дерево с сотнями тысяч узлов, и я использую __slots__
, чтобы уменьшить потребление памяти. Я просто нашел очень странную ошибку и исправил ее, но я не понимаю поведения, которое я видел.
Здесь упрощенный пример кода:
class NodeBase(object):
__slots__ = ["name"]
def __init__(self, name):
self.name = name
class NodeTypeA(NodeBase):
name = "Brian"
__slots__ = ["foo"]
Затем я выполняю следующее:
>>> node = NodeTypeA("Monty")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 4, in __init__
AttributeError: 'NodeTypeA' object attribute 'name' is read-only
Нет ошибки, если NodeTypeA.name
не определен (сторона примечания: этот атрибут был там по ошибке, и у него не было причин быть там). Также нет ошибки, если NodeTypeA.__slots__
никогда не определяется, и поэтому имеет значение __dict__
.
То, что я не понимаю, заключается в следующем: почему существование переменной класса в суперклассе мешает установке переменной экземпляра в слот в дочернем классе?
Может кто-нибудь объяснить, почему эта комбинация приводит к ошибке object attribute is read-only
? Я знаю, что мой пример изобретателен и вряд ли будет преднамеренным в реальной программе, но это не делает это поведение менее странным.
Спасибо,
Джонатан