Python是個人最喜歡的語言,剛開始接觸Python時,總覺得有很多槽點,不太喜歡。后來,不知不覺中,就用的多了、習慣了、喜歡上了。Python的功能真的很強大,自己當初學習這門語言的時候,也記錄過很多的筆記,現慢慢把這些筆記發布出來,希望對大家有所幫助,對自己也算是一個總結。
關於Python默認參數,假如默認參數是可變對象是會有副作用的,這一點我一開始不是很理解,直到有一天,看到一篇博文說:一個函數參數的默認值,僅僅在該函數定義的時候,被賦值一次。如此,只有當函數第一次被定義的時候,才講參數的默認值初始化到它的默認值(如一個空的列表)。
聽到這個解釋,豁然開朗,解釋器試驗如下:
1 >>> def f(x = []): 2 print(id(x)) 3 x.append(1) 4 print x 5 print(id(x)) 6
7
8 >>> f() 9 38869952 # 可變默認參數是在原地更改!!!
10 38869952
11 >>> f() 12 38869952 # 再次調用時,可變默認參數還是引用最初定義的!!!
13 38869952
14 # 注意,默認參數是在定義時賦值,且僅僅賦值一次。
15 # 當函數多次被調用,並且沒有提供默認的參數值,就會從定義時賦值的地方取得值!
16 # 即使函數中給默認參數重新賦值了,下次調用還是會從定義賦值的地方取得值!
17 # 如以下的示例:當f2()多次調用,雖然在函數體里面給y重新賦值了,但是下次調用時
18 # 再次打印print id(x) 的結果也還是一樣的!
19 # 所以:
20 # 1. 假如默認參數是可變對象,則會在原處直接更改對象,下次調用參數時,默認參數已經
21 # 更改過的了。如f()函數。
22 # 2. 假如默認參數不可變,那么給函數中給 參數賦值時,參數會引用內存的其他地方。下次函數調用時
23 # 默認參數還是從定義時賦值處取得值,因此沒有副作用!
24 >>> def f2(y = None): 25 print(id(y)) 26 if not y: 27 y = [] 28 y.append(1) 29 print(id(y)) 30
31
32 >>> f2() 33 505672708 # 定義時默認參數引用這一塊內存。
34 38888872 # 函數體內賦值后,y引用其他地方。
35 >>> f2() 36 505672708 # 再次調用,y還是引用定義時賦值的內存處。
37 43910728 # 函數體內賦值后,y引用其他地方。
38 >>> f() 39 38869952
40 38869952
41 >>> f2() 42 505672708
43 43909408
44 >>> f2() 45 505672708
46 38868752
47 >>>
