Python初學 高階函式的使用

2021-08-27 21:10:34 字數 4871 閱讀 1321

目錄

1.高階函式的概念 

2.常用的內建高階函式

2.1 map()

2.2 reduce()

2.3 filter() 

2.4 sorted()

3.decorator裝飾器

4.偏函式 

要理解高階函式,必須先理解兩個概念:

變數可以指向函式

函式名其實就是指向函式的變數

f = abs

print f(-5)

#輸出為5

abs = len

print abs[-10]

#報錯,int沒有len()函式

print abs(['a', 'b'])

#輸出為2

高階函式就是可以使用函式作為引數的函式,如下所示:

def abs_add(x, y, f):

return f(x) + f(y)

print abs_add(-5, 9, abs)

#結果為14

python中常用的高階函式有map()、reduce()、filter()等,下面初步介紹一下用法及注意事項

map()是 python 內建的高階函式,它接收乙個函式 f 和乙個 list,並通過把函式 f 依次作用在 list 的每個元素上,得到乙個新的 list 並返回。

def format_name(s):

return s[0:1].upper() + s[1:].lower();

print map(format_name, ['adam', 'lisa', 'bart'])

#輸出結果為['adam', 'lisa', 'bart']

注意:map()函式不改變原有的 list,而是返回乙個新的 list。

reduce()同map()類似,也接受乙個函式 f 和乙個 list ,不同在於reduce()傳入的函式 f 必須接收兩個引數,reduce()對list的每個元素反覆呼叫函式f,並返回最終結果值。

def prod(x, y):

return x * y

print reduce(prod, [2, 4, 5, 7, 12])

#執行結果為3360

#2*4*5*7*12

#reduce()還可以接收第3個可選引數,作為計算的初始值。

print reduce(prod, [2, 4, 5, 7, 12], 100)

#執行結果為336000

#100*2*4*5*7*12

filter()函式接收乙個函式 f 和乙個list,這個函式 f 的作用是對每個元素進行判斷,返回 true或 false,filter()根據判斷結果自動過濾掉不符合條件的元素,返回由符合條件元素組成的新list。

import math

def is_sqr(x):

return x and math.sqrt(x)%1 == 0

#在return語句中,if語句通常可以使用and來代替,因為和運算子乙個為否均為否

print filter(is_sqr, range(1, 101))

#輸出結果為[1, 4, 9, 16, 25, 36, 49, 64, 81, 100]

sorted()也是乙個高階函式,它可以接收乙個比較函式來實現自定義排序,比較函式的定義是,傳入兩個待比較的元素 x, y,如果 x 應該排在 y 的前面,返回 -1,如果 x 應該排在 y 的後面,返回 1。如果 x 和 y 相等,返回 0

def cmp_ignore_case(s1, s2):

if s1.lower() < s2.lower():

return -1

if s1.lower() > s2.lower():

return 1

return 0

print sorted(['bob', 'about', 'zoo', 'credit'], cmp_ignore_case)

在了解decorator裝飾器之前我們需要了解兩個概念:

1.返回函式:顧名思義,函式可以被函式返回

def calc_prod(lst):

def prod( x, y ):

return x * y

def g():

return reduce(prod, lst)

return g

#返回g函式,可以起到「延遲計算」的作用,只有在呼叫的時候才會計算

f = calc_prod([1, 2, 3, 4])

print f()

#此時才計算,輸出24

2.閉包:

內層函式引用了外層函式的變數(引數也算變數),然後返回內層函式的情況,稱為閉包(closure)。

閉包的特點是返回的函式還引用了外層函式的區域性變數,所以,要正確使用閉包,就要確保引用的區域性變數在函式返回後不能變。因此,返回函式不要引用任何迴圈變數,或者後續會發生變化的變數。如要使用,看以下**:

def count():

fs =

for i in range(1, 4):

def f(temp):

def g():

return temp * temp

return g

r = f(i)

return fs

#如果沒有f()函式,計算的時候只會計算i=3的情況,因為此時for會執行到i=3

f1, f2, f3 = count()

print f1(), f2(), f3()

#輸出結果為1,4,9

decorator裝飾器主要是用於增強函式的功能,避免給每個函式額外編寫重複**,比如給函式增加日誌、檢測效能等,為了簡化裝飾器的呼叫,python通常使用@

python的 decorator 本質上就是乙個高階函式,它接收乙個函式作為引數,然後,返回乙個新函式。

import time

def performance(f):

def fn(x):

print 'call '+ f.__name__ + '() in ' , time.localtime(time.time());

return f(x)

return fn

#這樣就給原函式f增加了乙個列印日誌和時間的功能

#這是不帶引數的decorator

@performance

def factorial(n):

return reduce(lambda x,y: x*y, range(1, n+1))

#@performance就相當於 factorial = performance(factorial)

print factorial(10)

#帶引數的decorator相比於不帶引數的需要額外增加一些**

def performance(unit):

def performance_decorator(f):

print 'call '+ f.__name__ + '()' + unit , time.localtime(time.time())

return f(*args, **kw)

return performance_decorator

#這樣就可以為decorator傳入一些引數

@performance('ms')

def factorial(n):

return reduce(lambda x,y: x*y, range(1, n+1))

print factorial(10)

注:@decorator可以動態實現函式功能的增加,但是,經過@decorator「改造」後的函式,和原函式相比,除了功能多一點外,有沒有其它不同的地方?

其實@decorator是建立了乙個新的函式,函式名、__doc__等函式的屬性都已經改變,我們可以使用python內建的functools來把原函式的一些屬性複製到新函式中

import time, functools

def performance(unit):

def perf_decorator(f):

@functools.wraps(f)

print "call " + f.__name__ + '()'

return f(*args, **kw)

return perf_decorator

@performance('ms')

def factorial(n):

return reduce(lambda x,y: x*y, range(1, n+1))

print factorial.__name__

import functools

sorted_ignore_case = functools.partial(sorted, cmp=lambda s1, s2: cmp(s1.upper(), s2.upper()))

#利用functools.partial()可以把乙個引數多的函式變成乙個引數少的新函式,少的引數需要在建立時指定預設值,有點類似於偏導數,乙個不變,只考慮另乙個引數,在這裡,不變的引數需要指定

print sorted_ignore_case(['bob', 'about', 'zoo', 'credit'])

#輸出結果為['about', 'bob', 'credit', 'zoo']

python初學函式 python 初學函式

len s 金老闆小 len s def my len 自定義函式 i 0 for k in s i 1 print i length my len print length 函式 定義了之後,可以在任何需要它的地方呼叫 沒有返回長度,只是單純的列印 返回的重要性 a,b len a 內建函式 le...

python 高階函式的使用

1.變數是可以指向函式的!abs 是內建函式 if name main print abs 8 f abs 變數指向於函式 print f 9 結果89 2.函式名其實就是指向函式的乙個變數 例如 如果把這個內建函式指向於另外的函式,就無法使用了,見下 print 函式名 abs abs len a...

Python高階函式的使用

又被稱之為匿名函式 格式 lambda 引數列表 函式體 def add x,y return x y print add 3,4 output 7add lambda lambda x,y x y add lambda 3,4 output 7三元運算子通常在python裡被稱為條件表示式,這些表...