Общий пример, когда речь идет о классе атрибутов в питоне, заключается в следующем:Почему назначение атрибутов класса в python ведет себя как присвоение переменных instace?
Python 2.7.6 (default, Sep 9 2014, 15:04:36)
>>> class B(object):
... cv = []
...
>>> b1 = B()
>>> b2 = B()
>>> b1.cv, b2.cv, B.cv
([], [], [])
>>> b1.cv.append(1)
>>> b1.cv, b2.cv, B.cv
([1], [1], [1])
>>> b2.cv.append(2)
>>> b1.cv, b2.cv, B.cv
([1, 2], [1, 2], [1, 2])
>>> B.cv.append(3)
>>> b1.cv, b2.cv, B.cv
([1, 2, 3], [1, 2, 3], [1, 2, 3])
Это показывает, что атрибут класса распределяется между классом и всеми экземплярами.
Но вот что происходит, когда мы переназначить значение атрибута класса, то есть без мутации исходного объекта, ограниченного атрибуту класса:
>>> class A(object):
... cv = 0
...
>>> a1 = A()
>>> a2 = A()
>>> a1.cv, a2.cv, A.cv
(0, 0, 0)
>>> a1.cv = 1
>>> a1.cv, a2.cv, A.cv
(1, 0, 0)
>>> a2.cv = 2
>>> a1.cv, a2.cv, A.cv
(1, 2, 0)
>>> A.cv = 3
>>> a1.cv, a2.cv, A.cv
(1, 2, 3)
Здесь мы можем видеть, что каждый раз, когда этот атрибут класса хранит его уникальное значение, и оно не будет переопределено в следующих назначениях, применяемых как в пространствах имен экземпляров, так и в классе.
Почему такое поведение выглядит следующим образом?
Я не могу понять, что это за логика может привести к тому, что это приводит к так «не имеющим отношения к делу» для «неизменяемых» (A) и «изменчивых» (B) случаев. Это заставляет меня думать о " нет никакого смысла использовать переменные класса», поскольку они могут быть склонны к ошибкам ...
Я надеюсь, что это я, кто не видит свет в этом туннеле ...
Эффекты класса можно эффективно использовать, если вы не собираетесь использовать их через экземпляры. Например, мне нравится управлять группой объектов одного класса в атрибутах класса. Если вы когда-либо слышали о Pygame, я чаще всего использую эту технику. –
Да, когда я вижу это, я подумал: «a1.cv !? a2.cv !? это статические переменные класса! и я нахожу это довольно обескураживающим, что Python позволяет смешивать и сопоставлять, как он используется. Я бы воздержался от постоянного доступа к классу static через члены экземпляра и никогда не знал, что есть проблема. Что касается того, почему Python позволяет вам выполнить приведенный выше код, я думаю, это объясняется в нижеследующем ответе, но кажется, что это хороший способ попасть в неприятности: p –
@MalikBrahimi, было бы здорово, если бы вы предоставили какой-то крошечный пример такой техники, просто чтобы понять реальный случай, когда это можно использовать ... И поместите некоторую ссылку на gist или pastebin или что-то еще ... Спасибо! – yashaka