2013-05-15 56 views
0

我只是有一个令人费解的问题abou在python中的类属性。 考虑下面的下面的类:python类属性:意外的行为

class A: 
    __lst = [] 
    def add(self, str): 
     self.__lst.append(str) 
     print len(self.__lst) 

我试图使两个实例x和y和我得到这个:

>>> x = A() 
>>> x.add('aaa') 
1 
>>> x.add('bbb') 
2 
>>> y = A() 
>>> y.add('aaa') 
3 
>>> y.add('bbb') 
4 

我期待的是y的实例将拥有的单独副本列表属性,但似乎即使您使用另一个对象将元素添加到列表中,列表也会变大。这很奇怪。

有没有人可以在这个问题上给我启发? 提前感谢您的帮助。 :-)

+2

“我期待y的实例将有一个单独的列表属性副本” - 您为什么期望这样?这是一个班级属性(你使用这个术语后似乎知道的一个概念),当然它属于班级,而不是实例。 – millimoose

+1

可能是因为Python不只是具有不同语法的java –

+0

对不起,我指的是属性本身,这意味着实例x的列表属性与实例y的列表属性无关。 – rbolante

回答

1

如果您在类体内定义了一个属性,那么它将是一个类属性,并且它将被所有实例共享。在您的代码self.__lst将被作为A.__lst的参考。

要为每个属性单独的列表,将其定义为self.__lst__init__()函数中:

class A(object): 
    def __init__(self): 
     self.__lst = [] 

    def add(self, s): 
     self.__lst.append(s) 
     print len(self.__lst) 

除了上面提到的变化,我也做了一些小的修改,以便您的代码如下几个Python最佳实践:从objectnew-style class)继承而不使用str(或任何其他内置名称)作为变量名称。

+0

它的工作!非常感谢F.J.的帮助:-) – rbolante

0

在类中声明的变量而不是self是类级别的属性(例如您的__lst)。它们相当于Java的static。如果您希望您的财产对所有实例都是唯一的,则需要通过self(即self.__lst)声明它们。