函數(shù)傳值問題
先看一個例子:
# -*- coding: UTF-8 -*- def chagne_number( b ): b = 1000 b = 1 chagne_number(b) print( b )
最后輸出的結(jié)果為:
1
這里可能有些人會有疑問,為啥不是通過函數(shù)chagne_number更改了 b 的值嗎?為啥沒有變化,輸出的結(jié)果還是 1 ,這個問題很多編程語言都會講到,原理解釋也是差不多的。
這里主要是函數(shù)參數(shù)的傳遞中,傳遞的是類型對象,之前也介紹了 Python 中基本的數(shù)據(jù)類型等。而這些類型對象可以分為可更改類型和不可更改的類型
在 Python 中,字符串,整形,浮點型,tuple 是不可更改的對象,而 list , dict 等是可以更改的對象。
例如:
不可更改的類型:變量賦值 a = 1,其實就是生成一個整形對象 1 ,然后變量 a 指向 1,當(dāng) a = 1000 其實就是再生成一個整形對象 1000,然后改變 a 的指向,不再指向整形對象 1 ,而是指向 1000,最后 1 會被丟棄
可更改的類型:變量賦值 a = [1,2,3,4,5,6] ,就是生成一個對象 list ,list 里面有 6 個元素,而變量 a 指向 list ,a[2] = 5則是將 list a 的第三個元素值更改,這里跟上面是不同的,并不是將 a 重新指向,而是直接修改 list 中的元素值。
這也將影響到函數(shù)中參數(shù)的傳遞了:
不可更改的類型:類似 c++ 的值傳遞,如 整數(shù)、字符串、元組。如fun(a),傳遞的只是 a 的值,沒有影響 a 對象本身。比如在 fun(a)內(nèi)部修改 a 的值,只是修改另一個復(fù)制的對象,不會影響 a 本身。
可更改的類型:類似 c++ 的引用傳遞,如 列表,字典。如 fun(a),則是將 a 真正的傳過去,修改后 fun 外部的 a 也會受影響
因此,在一開始的例子中,b = 1,創(chuàng)建了一個整形對象 1 ,變量 b 指向了這個對象,然后通過函數(shù) chagne_number 時,按傳值的方式復(fù)制了變量 b ,傳遞的只是 b 的值,并沒有影響到 b 的本身。具體可以看下修改后的實例,通過打印的結(jié)果更好的理解。
# -*- coding: UTF-8 -*- def chagne_number( b ): print('函數(shù)中一開始 b 的值:{}' .format( b ) ) b = 1000 print('函數(shù)中 b 賦值后的值:{}' .format( b ) ) b = 1 chagne_number( b ) print( '最后輸出 b 的值:{}' .format( b ) )
打印的結(jié)果:
函數(shù)中一開始 b 的值:1 函數(shù)中 b 賦值后的值:1000 最后輸出 b 的值:1
當(dāng)然,如果參數(shù)中的是可更改的類型,那么調(diào)用了這個函數(shù)后,原來的值也會被更改,具體實例如下:
# -*- coding: UTF-8 -*- def chagne_list( b ): print('函數(shù)中一開始 b 的值:{}' .format( b ) ) b.append(1000) print('函數(shù)中 b 賦值后的值:{}' .format( b ) ) b = [1,2,3,4,5] chagne_list( b ) print( '最后輸出 b 的值:{}' .format( b ) )
輸出的結(jié)果:
函數(shù)中一開始 b 的值:[1, 2, 3, 4, 5] 函數(shù)中 b 賦值后的值:[1, 2, 3, 4, 5, 1000] 最后輸出 b 的值:[1, 2, 3, 4, 5, 1000]