Python默認(rèn)參數(shù)如何才能進(jìn)行求值操作
和很多高級編程語言一樣,Python默認(rèn)參數(shù)也有很大的用處。但是我們在使用的時候會出現(xiàn)不少的問題,這些問題就需要我們用相關(guān)的知識進(jìn)行解答。當(dāng)默認(rèn)參數(shù)是數(shù)值類型時,一切都很美好:
- >>> def function(a, b = 1000000):
- b +=a
return b 如果你喜歡,你可以在一段代碼中無數(shù)次的調(diào)用這個函數(shù),只要你參數(shù)一樣,結(jié)果應(yīng)該都一樣。比如:function(1)總是會返回1000001。但是默認(rèn)參數(shù)是其他類型(如列表)時就沒那么美好了:
- >>> def function(a, b = []):
- b.append(a)
- print(b)
這時你如果在一段代碼中持續(xù)的調(diào)用該函數(shù),將會發(fā)生或許令人意外的情況:第一次調(diào)用function(1)的時候,很正常,會打印出[1],但是第二次再調(diào)用function(1),將會打印出[1,1]。這是為什么呢?不要緊,使用Python默認(rèn)參數(shù)我們有辦法檢查一下是哪里出了毛病。這里我們可以在每一次調(diào)用函數(shù)的時候打印出b的ID。Python中一個對象的ID在其生命周期中是唯一的,和其他高級語言中所說的對象的地址一樣。如果第二段代碼中的b對象其ID一樣,說明兩次調(diào)用都使用的同一個對象,換句話說,Python默認(rèn)參數(shù)的求值操作在其生命周期中只發(fā)生一次(第一次)??梢允褂靡韵碌拇a測試我們的想法:
- def function1(a,b=100000):
- b+=a
- print("b = {0} with the id of {1}".format(b,id(b)))
- def function2(a,b=[]):
- b.append(a)
- print("b = {0} with the id of {1}".format(b,id(b)))
- def test():
- function1(1)
- function1(1)
- function2(1)
- function2(1)
- if __name__ == '__main__':
- test()
得到的輸出如下:
- b = 100001 with the id of 33384304
- b = 100001 with the id of 33384304
- b = [1] with the id of 33341848
- b = [1, 1] with the id of 33341848
以上就是對Python默認(rèn)參數(shù)的詳細(xì)介紹。果然,從后面兩條結(jié)果中可以看到列表b在兩次調(diào)用時都是使用的同一個對象,看來之前的猜想是正確的。對非數(shù)值類型的默認(rèn)參數(shù),只會在第一次調(diào)用時進(jìn)行求值(取地址)操作。后面的所有調(diào)用都發(fā)生在同一個位置的對象上。只有字符串類型不受此限制,因?yàn)閟tring本身是不可變的(immutable)的,每一次修改它都會創(chuàng)建一個新的對象。
【編輯推薦】