Я хочу поделиться некоторой информацией между всеми экземплярами некоторого класса и всеми его производными классами.
class Base():
cv = "some value" # information I want to share
def print_cv(self, note):
print("{}: {}".format(note, self.cv))
@classmethod
def modify_cv(cls, new_value):
# do some class-specific stuff
cls.cv = new_value
class Derived(Base):
pass
b = Base()
d = Derived()
b.print_cv("base")
d.print_cv("derived")
Вывод соответствует ожиданиям (экземпляры обоих классов видят правильный атрибут класса):
base: some value
derived: some value
Я могу изменить значение этого атрибута класса, и все по-прежнему в порядке:
# Base.cv = "new value"
b.modify_cv("new value")
b.print_cv("base") # -> base: new value
d.print_cv("derived") # -> derived: new value
Пока все хорошо. Проблема в том, что «соединение» между базовыми и производными классами может быть разорвано, если я получу доступ к cv
через производный класс:
# Derived.cv = "derived-specific value"
d.modify_cv("derived-specific value")
b.print_cv("base") # -> base: new value
d.print_cv("derived") # -> derived: derived-specific value
Такое поведение ожидается, но это не то, что я хочу!
Я понимаю, почему a
и b
видят разные значения cv
- потому что они являются экземплярами разных классов. Я переопределил значение cv
в производном классе, и теперь производный класс ведет себя по-другому, я использовал эту функцию много раз.
Но для моей текущей задачи мне нужно, чтобы a
и b
всегда использовали один и тот же cv
!
UPDATE
Я обновил вопрос, и теперь он лучше описывает реальную ситуацию. На самом деле я не изменил значение cv
следующим образом:
Base.cv = "new value"
модификации были сделаны в некоторых методах класса (фактически все эти методы класса были реализованы в Base
классе).
И теперь решение стало очевидным, мне просто нужно немного изменить метод:
class Base():
@classmethod
def modify_cv(cls, new_value):
#cls.cv = new_value
Base.cv = new_value
Спасибо всем за обсуждение и идеи (вначале я собирался использовать методы получения / установки и атрибут уровня модуля)