了解应该绑定到对象实例的类范围变量

时间:2014-02-01 06:35:27

标签: python oop

这是一个为玩家分配符号的类。它应该接受移动并将移动添加到玩家的现有移动存储库中。

class Player:
   ...:     positions = []
   ...:     def __init__(self,symbol):
   ...:         self.symbol = symbol
   ...:     def move(self,position):
   ...:         self.position = position
   ...:         self.positions.append(self.position)

我的问题是职位在全球范围内表现出来"从某种意义上说,它没有绑定到对象实例,以证明:

>>>a = Player('x')
>>>b = Player('y')
>>>a.move(1)
>>>b.positions
[1]

5 个答案:

答案 0 :(得分:4)

当你说,

class Player:
    positions = []

positions将是一个类变量,并且该类的所有实例都使用相同的对象。您可以通过此确认

player1, player2 = Player(), Player()
print player1.positions is player2.positions    # True
print Player.positions is player1.positions     # True

如果要为positions的每个实例创建实例变量(单独的Player变量),可以在__init__函数中创建它。它是一个特殊的初始化函数,它将当前实际对象作为第一个参数。您可以创建positions变量并将其附加到该对象,如此

class Player:
    def __init__(self):
        self.positions = []

player1, player2 = Player(), Player()
print player1.positions is player2.positions    # False

在这里,self引用新构造的对象,并且您要通过self.positions在该对象中创建一个新变量,并使用空列表初始化它

self.positions = []

因此,每当您创建Player的新实例时,self将引用创建的新实例,并且将在每个实例上创建新变量positions,这意味着单独positions 1}}每个实例的变量。

每当调用move时,您就不必在position上创建新的self变量。相反,你可以这样做

def move(self, position):
    self.positions.append(position)

如果您使用的是Python 2.x,最好使用新的样式类,比如

class Player(object):
    def __init__(self):
        self.positions = []

答案 1 :(得分:1)

__init__方法中声明它。在__init__方法之外声明的Anyhting将是一个类属性,并将在该类的所有实例之间共享。

您无需传递任何内容:

class Player: 
   ...:     def __init__(self,symbol):
   ...:         self.symbol = symbol
                self.positions = []
   ...:     def move(self,position):
   ...:         self.position = position
   ...:         self.positions.append(self.position)

答案 2 :(得分:1)

是的,您需要将类变量设置为实例变量,该变量将仅绑定到特定实例。

目前,positions = []是类变量,可以从所有实例访问。因此,您最好分配给特定的实例变量。

您可以通过定义内部__init__()来执行此操作,该内容将在您创建该类的实例时调用。

答案 3 :(得分:1)

IMO你也想在init中将self.position初始化为None,以免你遇到这个错误:

p = Player() 
p.position 
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: Player instance has no attribute 'position'

所以你想要这个:

class Player(object):     # making it a new-style class
    def __init__(self, ...):
        ...
        self.position = None

答案 4 :(得分:1)

  

我的问题是,位置表现为“全局”,因为它不依赖于对象实例,以演示

是的,这是语言的设计。 Python遵循的规则与其他支持OO的现代语言不同,但它非常简单易懂:您在class块中编写的所有内容都描述了类的一部分。 (请记住,在Python中,一切都是对象 - 包括类本身。)

所以我真的不明白问题所在。您显然已经知道如何制作属于实例的内容(提示:您已经使用symbol进行了此操作)。您可能只需要重新考虑您的设计,并更清楚您打算发生的事情。