了解Python的传递函数参数的对象风格 [英] Understanding Python's call-by-object style of passing function arguments
问题描述
我不确定我是否理解Python调用通过传递函数参数的对象风格的概念(这里解释 http://effbot.org/zone/call-by-object.htm )。有没有足够的例子可以很好地阐明这个概念(或者我的google-fu可能很弱!):D
我写了这个小小的人工Python程序试着理解这个概念:
$ $ $ $ $ $ $ $ deffoo $ it $ $ $ $ $ $ $
print id(itnumber),itnumber
print id(ittuple),ittuple
itlist.append(3.4)
print id(itlist),itlist
itdict ['mary'] = 2.3
print id(itdict),itdict
#初始化一个数字,一个元组,列表和字典
tnumber = 1
print id(tnumber),tnumber
ttuple =(1,2,3)
print id(ttuple) ,ttuple
tlist = [1,2,3]
print id(tlist),tlist
tdict = tel = {'jack':4098,'' sape':4139}
print'-------'
#调用一个函数并测试它
foo(tnumber,ttuple,tlist,tdict)
打印'-------'
#Tes t行为在函数调用后超过
print id(tnumber),tnumber
print id(ttuple),ttuple
print id(tlist),tlist
print id(tdict) ,tdict
程序的输出是
146739376 1
3075201660(1,2,3)
3075103916 [1,2,3]
3075193004 {'sape':4139,'' jack':4098}
---------
146739364 2
3075201660(1,2,3)
3075103916 [ 1,2,3,3.4]
3075193004 {'sape':4139,'jack':4098,'mary':2.3}
---------
146739376 1
3075201660(1,2,3)
3075103916 [1,2,3,3.4]
3075193004 {'sape':4139,'jack' :4098,'mary':2.3}
正如您所看到的,除了传入的整数,对象ID(据我所知,指memeory位置)保持不变。
所以在整数情况下,它被(有效地)按值传递,另一个数据结构被(有效地)通过引用传递。我试着改变列表,数字和字典来测试数据结构是否已经改变。这个数字不在名单和
字典中。
我在上面使用了这个词这个词,因为参数传递的'调用对象'风格似乎表现为两种方式,这取决于在上面的代码中传递的数据结构 对于更复杂的数据结构(比如numpy数组等),有没有什么快速的经验法则可以让 关键区别在于,在C风格语言中,变量是内存中的一个框,东东。在Python中,变量是一个名字。 Python既不是按引用也不是按值调用。这是更明智的东西! (事实上,在我学习更多常用语言之前,我学会了Python,因此对于我来说,按值调用和按引用调用看起来很奇怪。) 在Python中有 和名称。列表,整数,字符串和自定义对象都是事物。 的意思是构建一个新的东西 表示构建一个新的东西 的意思是构造一个新事物 I am not sure I understand the concept of Python's call by object style of passing function arguments (explained here http://effbot.org/zone/call-by-object.htm). There don't seem to be enough examples to clarify this concept well (or my google-fu is probably weak! :D) I wrote this little contrived Python program to try to understand this concept The output of the program is As you can see , except for the integer that was passed, the object id's (which as I understand refers to memeory location) remain unchanged. So in the case of the integer, it was (effectively) passed by value and the other data structure were (effectively) passed by reference. I tried changing the list , the number and the dictionary to just test if the data-structures were changed in place. The number was not bu the list and the
dictionary were. I use the word effectively above, since the 'call-by-object' style of argument passing seems to behave both ways depending on the data-structure passed in the above code For more complicated data structures, (say numpy arrays etc), is there any quick rule of thumb to
recognize which arguments will be passed by reference and which ones passed by value? The key difference is that in C-style language, a variable is a box in memory in which you put stuff. In Python, a variable is a name. Python is neither call-by-reference nor call-by-value. It's something much more sensible! (In fact, I learned Python before I learned the more common languages, so call-by-value and call-by-reference seem very strange to me.) In Python, there are things and there are names. Lists, integers, strings, and custom objects are all things. means "construct a new thing means "construct a new thing means "construct a new thing 这篇关于了解Python的传递函数参数的对象风格的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
识别哪个参数将通过引用传递,哪些通过值传递?
x
, y
和 z
是名称。写作
x = []
[]
并给它起名叫 x
。写作
x = []
foo = lambda x:x.append(无)
foo x)
[] $ c $使用名称
f
构造一个新函数(这是另一回事),并调用对于名称
。现在 x
的东西,c $ c> foo foo
只是将 None
附加到所有收到的内容中,所以这会减少为append None
到空的列表。写作
x = 0
def foo(x):
x + = 1
foo (x)
0
名称 x
,构造一个新函数 foo
,并调用 foo
on x
。在 foo
里面,赋值只是说重命名 x
为1加上它曾经是的,但那并不是' t改变 0。def foo( itnumber, ittuple, itlist, itdict ):
itnumber +=1
print id(itnumber) , itnumber
print id(ittuple) , ittuple
itlist.append(3.4)
print id(itlist) , itlist
itdict['mary'] = 2.3
print id(itdict), itdict
# Initialize a number, a tuple, a list and a dictionary
tnumber = 1
print id( tnumber ), tnumber
ttuple = (1, 2, 3)
print id( ttuple ) , ttuple
tlist = [1, 2, 3]
print id( tlist ) , tlist
tdict = tel = {'jack': 4098, 'sape': 4139}
print '-------'
# Invoke a function and test it
foo(tnumber, ttuple, tlist , tdict)
print '-------'
#Test behaviour after the function call is over
print id(tnumber) , tnumber
print id(ttuple) , ttuple
print id(tlist) , tlist
print id(tdict), tdict
146739376 1
3075201660 (1, 2, 3)
3075103916 [1, 2, 3]
3075193004 {'sape': 4139, 'jack': 4098}
---------
146739364 2
3075201660 (1, 2, 3)
3075103916 [1, 2, 3, 3.4]
3075193004 {'sape': 4139, 'jack': 4098, 'mary': 2.3}
---------
146739376 1
3075201660 (1, 2, 3)
3075103916 [1, 2, 3, 3.4]
3075193004 {'sape': 4139, 'jack': 4098, 'mary': 2.3}
x
, y
, and z
are names. Writingx = []
[]
and give it the name x
". Writingx = []
foo = lambda x: x.append(None)
foo(x)
[]
with name x
, construct a new function (which is another thing) with name foo
, and call foo
on the thing with name x
". Now foo
just appends None
to whatever it received, so this reduces to "append None
to the the empty list". Writingx = 0
def foo(x):
x += 1
foo(x)
0
with name x
, construct a new function foo
, and call foo
on x
". Inside foo
, the assignment just says "rename x
to 1 plus what it used to be", but that doesn't change the thing 0.