本文將介紹筆者在工作中遇到的Python的一個坑,那就是使用列表作為預設引數。
我們知道,在Python中,列表(list)是可變物件,所以列表的內容可能會在函式內改變。另一個需要注意的是,使用列表作為函式的預設引數時,列表的內容變化情況。
首先,我們看以下的程式碼例子:
def add(x, lst=[]):
if x not in lst:
lst.append(x)
return lst
def main():
list1 = add(1)
print(list1)
list2 = add(2)
print(list2)
list3 = add(3, [11, 12, 13, 14])
print(list3)
list4 = add(4)
print(list4)
main()
你可能以為輸出的結果會是:
[1]
[2]
[11, 12, 13, 14, 3]
[4]
但事實上,該程式輸出的結果是:
[1]
[1, 2]
[11, 12, 13, 14, 3]
[1, 2, 4]
這是為什麼呢?函式add的功能是當x不在列表中時,將x追加給列表lst。當函式第一次執行時,引數lst的預設值[]被建立。這個預設值只會被建立一次。add(1)將1加到lst。當函式再次被呼叫時,lst是[1]而不是[],因為lst只被建立一次。當引數的lst為[11,12,13,14]時,lst就是[11,12,13,14]。list4呼叫函式時,使用預設引數,因此,現在預設引數lst為[1,2]。
為了更好地理解呼叫情況,可以在add函式中輸出lst的id,如以下程式碼:
def add(x, lst=[]):
print(id(lst))
if x not in lst:
lst.append(x)
return lst
def main():
list1 = add(1)
print(list1)
list2 = add(2)
print(list2)
list3 = add(3, [11, 12, 13, 14])
print(list3)
list4 = add(4)
print(list4)
main()
輸出結果如下:
4469603648
[1]
4469603648
[1, 2]
4469670472
[11, 12, 13, 14, 3]
4469603648
[1, 2, 4]
可以看到,list1, list2, list4呼叫時預設引數的id並沒有發生改變,而list3的id發生了改變。
這是Python使用列表作為預設引數的一個坑。那麼,如何避免踩坑呢?如果想要使用預設列表在每次函式呼叫時都是[],可以像下面的程式那樣修改函式引數:
def add(x, lst=None):
if lst is None:
lst = []
if x not in lst:
lst.append(x)
return lst
def main():
list1 = add(1)
print(list1)
list2 = add(2)
print(list2)
list3 = add(3, [11, 12, 13, 14])
print(list3)
list4 = add(4)
print(list4)
main()
輸出的結果如下:
[1]
[2]
[11, 12, 13, 14, 3]
[4]
本次分享到此結束,感謝閱讀~
注意:本人現已開通微信公眾號: Python爬蟲與演算法(微訊號為:easy_web_scrape), 歡迎大家關注哦~~