为了账号安全,请及时绑定邮箱和手机立即绑定

python类实例变量和类变量

python类实例变量和类变量

慕码人8056858 2019-10-21 09:23:20
我在理解类/实例变量如何在Python中工作时遇到问题。我不明白为什么当我尝试这段代码时列表变量似乎是一个类变量class testClass():    list = []    def __init__(self):        self.list.append('thing')p = testClass()print p.listf = testClass()print f.list输出:['thing']['thing', 'thing']当我这样做时,它似乎是一个实例变量class testClass():    def __init__(self):        self.list = []        self.list.append('thing')p = testClass()print p.listf = testClass()print f.list输出:['thing']['thing']
查看完整描述

3 回答

?
慕容森

TA贡献1853条经验 获得超18个赞

这是因为Python使用.。解析名称的方式。在编写时self.list,Python运行时首先尝试list通过在实例对象中查找名称来解析名称,如果找不到,则在类实例中进行查找。


让我们逐步研究它


self.list.append(1)

list对象中有名称self吗?

是的:使用它!完。

否:转到2。

list对象的类实例中是否有名称self?

是的:使用它!完

否:错误!

但是,当您绑定名称时,情况有所不同:


self.list = []

list对象中有名称self吗?

是:覆盖它!

否:绑定!

因此,这始终是一个实例变量。


您的第一个示例list在类实例中创建一个,因为这是当时的活动范围(没有self任何地方)。但是您的第二个示例list在的范围内显式创建了一个self。


这个例子更有趣:


class testClass():

    list = ['foo']

    def __init__(self):

        self.list = []

        self.list.append('thing')


x = testClass()

print x.list

print testClass.list

del x.list

print x.list

那将打印:


['thing']

['foo']

['foo']

删除实例名称后,可以通过self引用看到类名称。


查看完整回答
反对 回复 2019-10-21
?
HUX布斯

TA贡献1876条经验 获得超6个赞

Python有关于查找名称的有趣规则。如果您真的想改变主意,请尝试以下代码:


class testClass():

    l = []

    def __init__(self):

        self.l = ['fred']

这将给每个实例一个变量l,该变量将屏蔽类变量l。如果这样做,您仍然可以使用class变量self.__class__.l。


我的想法是……只要您这样做instance.variable(即使对于方法名,它们只是值恰好是函数的变量),它都会在实例的字典中查找它。如果找不到它,它将尝试在实例的“类”字典中查找它。仅当变量被“读取”时。如果将其分配给它,它将始终在实例字典中创建一个新条目。


查看完整回答
反对 回复 2019-10-21
?
守着一只汪

TA贡献1872条经验 获得超3个赞

在第一个示例中,list是类的一个属性,由该类的所有实例共享。这意味着您甚至可以在没有类型对象的情况下访问它testClass:


>>> class testClass():

...     list = []

...     def __init__(self):

...             self.list.append("thing")

... 

>>> testClass.list

[]

>>> testClass.list.append(1)

>>> testClass.list

[1]

但是所有对象都list与该类以及彼此共享该属性:


>>> testObject = testClass()

>>> testObject.list

[1, 'thing']

>>> testClass.list

[1, 'thing']

>>> 

>>> testObject2 = testClass()

>>> testClass.list

[1, 'thing', 'thing']

>>> testObject2.list

[1, 'thing', 'thing']


查看完整回答
反对 回复 2019-10-21
  • 3 回答
  • 0 关注
  • 483 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信