python3 入門 (三) 函數與lambda表達式、閉包


函數 是組織好的、可重復使用的、用來實現單一或相關聯功能的代碼段。

 

  • 函數代碼塊以def關鍵詞開頭,后接函數標識符名稱和圓括號()
  • 任何傳入參數和自變量必須放在圓括號中間。圓括號之間可以用於定義參數
  • 函數的第一行語句可以選擇性地使用文檔字符串—用於存放函數說明
  • 函數內容以冒號起始,並且縮進
  • Return[expression]結束函數,選擇性地返回一個值給調用方。不帶表達式的return相當於返回 None

 

函數的定義

1 def test0():
2     "函數_文檔字符串"
3     print('函數內部')
4 
5 print(test0.__doc__)  # 函數_文檔字符串

 

若采用默認參數定義函數,調用函數時,缺省參數的值如果沒有傳入,則被認為是默認值:

1 def test1(arg1='參數一', arg2='參數二'):
2     print('arg1:'+arg1)
3     print('arg2:'+arg2)
4 
5 test1()  # arg1:參數一  arg2:參數二
6 
7 # 默認情況下,參數值和參數名稱是按函數聲明中定義的的順序匹配起來的
8 test1('ice', 'cream')  # arg1:ice  arg2:cream
9 test1(arg2='cream', arg1='ice')  # arg1:ice  arg2:cream

 

不定長參數。加了星號(*)的變量名會存放所有未命名的變量參數。選擇不多傳參數也可:

 1 def test2(*args, param):
 2     print(len(args))
 3     for arg in args:
 4         print(arg)
 5     print(param)
 6 
 7 test2(1, 2, 3, 4, param='This is param')
 8 
 9 
10 def test3(param, *args):
11     print(param)
12     print(len(args))
13     for arg in args:
14         print(arg)
15 
16 test3('This is param', 1, 2, 3, 4)

 

所有參數(自變量)在Python里都是按引用傳遞。如果在函數里修改了參數,那么在調用這個函數的函數里,原始的參數也被改變了

 1 def test4(mylist):
 2     print(mylist)
 3     mylist.clear()
 4     print(mylist)
 5 
 6 mylist = [1, 2, 3, 4]
 7 test4(mylist)
 8 print(mylist)
 9 
10 # 輸出:
11 # [1, 2, 3, 4]
12 # []
13 # []

 

return語句[表達式]退出函數,選擇性地向調用方返回一個表達式。不帶參數值的return語句返回None

 1 def test5():
 2     return (1, 2, 3, 4)
 3 
 4 
 5 def test6():
 6     return 1, 2, 3, 4
 7 
 8 
 9 def test7():
10     return [1, 2, 3, 4]
11 
12 result = test5()
13 print(result)  # (1, 2, 3, 4)
14 
15 result = test6()
16 print(result)  # (1, 2, 3, 4)
17 
18 result = test7()
19 print(result)  # [1, 2, 3, 4]

 

內部函數。函數體內可以再定義函數:

 1 def outerFunc():
 2     print('Outer Funtion') 3 def innerFunc(): 4 print('Inner Function') 5  innerFunc() 6 7 outerFunc() 8 9 # 輸出: 10 # Outer Funtion 11 # Inner Function

 

函數變量作用域

 

定義在函數內部的變量擁有一個局部作用域,定義在函數外的擁有全局作用域

局部變量只能在其被聲明的函數內部訪問,而全局變量可以在整個程序范圍內訪問。調用函數時,所有在函數內聲明的變量名稱都將被加入到作用域中

 1 temp = 'ice cream'
 2 
 3 def test8():
 4     "全局變量可以在整個程序范圍內訪問"
 5     print(temp)
 6 
 7 
 8 def test9():
 9     inner_temp = 'ice'
10     print(inner_temp)
11 
12 print(temp)  # ice cream
13 test8()  # ice cream
14 test9()  # ice
15 
16 
17 # 局部變量只能在其被聲明的函數內部訪問
18 print(inner_temp)  # 報錯  name 'inner_temp' is not defined
19 
20 def test10():
21     print(temp)  # 報錯  local variable 'temp' referenced before assignment
22     temp = 'ice'
23     print(temp)

 

 

Python閉包

如果在一個內部函數里,對在外部作用域(但不是在全局作用域)的變量進行引用,那么內部函數就被認為是閉包(closure)。一個閉包就是你調用了一個函數A,這個函數A返回了一個函數B給你。這個返回的函數B就叫做閉包。你在調用函數A的時候傳遞的參數就是自由變量

 1 def FuncX(x):
 2     def FuncY(y):
 3         return x * y
 4     return FuncY
 5 
 6 tempFunc = FuncX(3)
 7 result = tempFunc(5)
 8 print(result)  # 15
 9 
10 result = FuncX(3)(5)
11 print(result)  # 15

 

 

匿名函數

python 使用 lambda 表達式來創建匿名函數

 

  • lambda只是一個表達式,函數體比def簡單很多
  • lambda的主體是一個表達式,而不是一個代碼塊。僅僅能在lambda表達式中封裝有限的邏輯進去
  • lambda函數擁有自己的名字空間,且不能訪問自有參數列表之外或全局名字空間里的參數
  • 雖然lambda函數看起來只能寫一行,卻不等同於C或C++的內聯函數,后者的目的是調用小函數時不占用棧內存從而增加運行效率

 

lambda函數的語法只包含一個語句: lambda [arg1 [,arg2,.....argn]]:expression 

使用如下:

1 square = lambda x : x**2
2 print(square(3))  # 9
3 
4 sum = lambda  x, y : x + y
5 print(sum(2, 3))  # 5

 

 

內置函數filter的使用

官方文檔內容如下:

filter(functioniterable)

Construct an iterator from those elements of iterable for which function returns true. iterable may be either a sequence, a container which supports iteration, or an iterator. If function is None, the identity function is assumed, that is, all elements of iterable that are false are removed.

 

function參數可傳入None、函數、lambda表達式,iterable參數傳入一個可迭代對象。

若function參數為None:返回可迭代對象中所有不為False的元素

若function參數為函數或lambda表達式:返回  將元素作為函數參數、函數返回值為True  的元素

 1 reslut = filter(None, [1, 0, False, True])
 2 print(list(reslut))  # [1, True]
 3 
 4 def odd(num):
 5     return num % 2
 6 
 7 reslut = filter(odd, range(10))
 8 print(list(reslut))  # [1, 3, 5, 7, 9]
 9 
10 reslut = filter(lambda num: num % 2, range(10) )
11 print(list(reslut))  # [1, 3, 5, 7, 9]

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM