在Python中传递self数据
能不能解释一下,为什么下面的 self.add(x)
和 self.data.append(x)
的效果是一样的?也就是说,self.add(x)
是怎么知道要把内容加到列表里的,因为我们并没有明确写 self.data.add(x)
?当我们调用 y.addtwice('cat')
的时候,'cat'
是被加到 'self'
里,而不是 self.data
。
class Bag:
def __init__(self):
self.data=[]
def add(self,x):
self.data.append(x)
return self.data
def addtwice(self,x):
self.add(x)
self.add(x)
return self.data
>>> y = Bag()
>>> y.add('dog')
['dog']
>>> y.addtwice('cat')
['dog', 'cat', 'cat']
5 个回答
我们来看看类 Bag
中的函数 add(self, x)
。
当这个函数被调用时,其中一个参数是 self,它代表的是对象本身。在这个例子中,就是调用了 add
函数的那个 Bag
实例。
所以在 add
函数里,调用 self.data.append(x)
实际上就是在对 Bag
的 data
列表执行 append 操作,也就是把元素 x
加到这个列表里。
对于 addtwice
函数也是一样。通过调用 add
两次,就会把两个元素添加到 Bag
的 data
列表中。
这两个函数都会返回 data
列表。
当我们说 y.addtwice('cat') 时,'cat' 是被添加到 'self' 而不是 self.data。
这个说法是不对的。实际上,cat
是被添加到 self.data
中的。你为什么会觉得它被添加到 self
呢?
y.add('dog')
和 Bag.add(y, 'dog')
是一样的。所以 add
实际上是在做 y.data.append('dog')
,通常我们会用 self
这个名字来表示。
y.addtwice('cat')
和 Bag.addtwice(y, 'cat')
也是一样的。所以 addtwice
实际上是做了两次 y.add('cat')
,这就等于做了两次 Bag.add(y, 'cat')
。所以 addtwice
实际上是在做 y.data.append('cat')
两次。
在每个 实例方法 中的 self
是一个自动添加的变量,它指向调用这个方法的 实例,在这个例子中就是 y
。
因为 addtwice
这个函数会调用在 self 上定义的方法,而 self.data 是一种“可变类型”,所以 addtwice
调用 add
的时候,会把 self.data 的值加到里面。接着,add
又会调用 self.data.append。
在计算机程序中调用一个函数时,可以把这个过程想象成一系列的替换,就像这样:
# -> means (substitution for)
# <= means "return"
y = Bag()
y.add('dog') ->
y.data.append(x) ->
#(machine code)
<= y.data
# at this point, at the command propmt, python will just print what was returned.
y.addtwice('cat')->
y.add('cat')->
y.data.append(x) ->
#(machine code)
<= y.data
#nothing cares about this return
y.add('cat')->
y.data.append(x) ->
#(machine code)
<= y.data
#nothing cares about this return either
<= y.data
# at this point, at the command propmt, python will just print what was returned.
不过,self
本身在这些情况下并没有被添加进去,真正被添加的是 self.data
。