尽管答案正确无误,但我想添加一些描述。
让我们进行一个小练习。
首先按照以下方式定义一个类:
class A:
temp = 'Skyharbor'
def __init__(self, x):
self.x = x
def change(self, y):
self.temp = y
那么我们在这里有什么?
- 我们有一个非常简单的类,它有一个名为
temp
的字符串属性。
- 一个
__init__
方法用于设置self.x
.
- 一个更改方法设置
self.temp
到目前为止都还很简单吧?现在让我们开始玩弄一下这个类。首先让我们初始化这个类:
a = A('Tesseract')
现在请执行以下操作:
>>> print(a.temp)
Skyharbor
>>> print(A.temp)
Skyharbor
嗯,a.temp
像预期的那样工作了,但是A.temp
怎么可能工作呢?它能工作是因为temp是一个类属性。Python中的所有东西都是对象。这里的A也是type类的一个对象。因此,属性temp是由类A持有的一个属性,如果你通过A
(而不是通过a
的实例)改变temp的值,改变后的值将反映在A
类的所有实例中。
让我们继续做到这一点:
>>> A.temp = 'Monuments'
>>> print(A.temp)
Monuments
>>> print(a.temp)
Monuments
有趣吧?并且请注意id(a.temp)
和id(A.temp)
仍然相同。
任何Python对象都会自动获得一个__dict__
属性,其中包含其属性列表。让我们调查一下我们示例对象的此字典包含哪些内容:
>>> print(A.__dict__)
{
'change': <function change at 0x7f5e26fee6e0>,
'__module__': '__main__',
'__init__': <function __init__ at 0x7f5e26fee668>,
'temp': 'Monuments',
'__doc__': None
}
>>> print(a.__dict__)
{x: 'Tesseract'}
请注意,
temp
属性列在
A
类的属性中,而
x
则列在实例中。那么如果
a
实例中甚至没有列出
a.temp
的定义值是如何得到的呢?这就是
__getattribute__()
方法的魔力。在Python中,使用点语法会自动调用此方法,因此当我们编写
a.temp
时,Python执行
a.__getattribute__('temp')
。该方法执行属性查找操作,即通过查看不同位置来查找属性的值。
__getattribute__()
的标准实现首先搜索对象的内部字典(
dict),然后搜索对象本身的类型。在这种情况下,
a.__getattribute__('temp')
首先执行
a.__dict__['temp']
,然后执行
a.__class__.__dict__['temp']
。
好的,现在让我们使用我们的
change
方法:
>>> a.change('Intervals')
>>> print(a.temp)
Intervals
>>> print(A.temp)
Monuments
现在我们使用了self
,print(a.temp)
的值与print(A.temp)
不同。
如果我们比较id(a.temp)
和id(A.temp)
,它们将是不同的。
list
是构造新列表的内置函数。您应使用大写字母为类命名。 - Marc Tudurí