天天看點

16. Python 高階函數、匿名函數

1.      高階函數

高階函數就是把函數當成參數傳遞的一種函數

舉例:

def add(x, y, f):

    return f(x) + f(y)

print (add(-8, 11, abs))

傳回結果:

19

① map() 函數

map() 函數接收兩個參數,一個是函數,一個是序列,map将傳入的函數依次作用到序列的每個元素,并把結果作為新的list傳回。

<a href="https://s4.51cto.com/oss/201711/02/b23428b8f3efd26ef3f5484b714cb0c9.png" target="_blank"></a>

lst = [1, 2, 3, 4, 5, 6, 7, 8, 9]

def f(x):

    return x * x

map(f, lst)

[1, 4, 9, 16, 25, 36, 49, 64, 81]

map(str, lst)

['1', '2', '3', '4', '5', '6', '7', '8', '9']

注釋:

map()傳入的第一個參數是f,即函數對象本身

② reduce() 函數

reduce把一個函數作用在一個序列[x1, x2, x3...]上,這個函數必須接收兩個參數,reduce把結果繼續和序列的下一個元素做累積計算。

格式:

        reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4)

#傳入的函數必須接受兩個參數;

#把可疊代對象的前兩個參數作為函數的實參,傳入到f函數中;

#把每次f運算的結果作為第一個實參,可疊代對象的下一個元素作為另一個實參,傳入函數f中;

#以此類推,最終得到結果。

def add(x, y):

    return x + y

reduce(add, [1, 3, 5, 7, 9])

結果:

25

③ filter() 函數

Python内建的filter()函數用于過濾序列。

和map()類似,filter()也接收一個函數和一個序列。和map()不同的時,filter()把傳入的函數依次作用于每個元素,然後根據傳回值是True還是False決定保留還是丢棄該元素。

例1,在一個list中,删掉偶數,隻保留奇數:

def is_odd(n):

    return n % 2 == 1

filter(is_odd, [1, 2, 4, 5, 6, 9, 10, 15])

結果:

[1, 5, 9, 15]

例2,把一個序列中的空字元串删掉:

def not_empty(s):

    return s and s.strip()

filter(not_empty, ['A', '', 'B', None, 'C', '  '])

['A', 'B', 'C']

④ sorted() 函數

排序算法

排序也是在程式中經常用到的算法。無論使用冒泡排序還是快速排序,排序的核心是比較兩個元素的大小。

通正常定,對于兩個元素x和y,如果認為x &lt; y,則傳回-1,如果認為x == y,則傳回0,如果認為x &gt; y,則傳回1,

這樣,排序算法就不用關心具體的比較過程,而是根據比較結果直接排序。

Python内置的sorted()函數

可以對list進行排序:

sorted([36, 5, 12, 9, 21])

[5, 9, 12, 21, 36]

可以對dict進行排序:

mm = dict( a=1, b=2, c=3, d=4)

print sorted(mm.itertiems(), key = lambda d:d[0], reverse = True)

此外,sorted()函數也是一個高階函數,它還可以接收一個比較函數來實作自定義的排序。

比如,如果要倒序排序,我們就可以自定義一個reversed_cmp函數:

def reversed_cmp(x, y):

    if x &gt; y:

        return -1

    if x &lt; y:

        return 1

    return 0

傳入自定義的比較函數reversed_cmp,就可以實作倒序排序:

sorted([36, 5, 12, 9, 21], reversed_cmp)

[36, 21, 12, 9, 5]

我們再看一個字元串排序的例子:

sorted(['bob', 'about', 'Zoo', 'Credit'])

['Credit', 'Zoo', 'about', 'bob']

預設情況下,對字元串排序,是按照ASCII的大小比較的,由于'Z' &lt; 'a',結果,大寫字母Z會排在小寫字母a的前面。

現在,我們提出排序應該忽略大小寫,按照字母序排序。

要實作這個算法,不必對現有代碼大加改動,隻要我們能定義出忽略大小寫的比較算法就可以:

def cmp_ignore_case(s1, s2):

    u1 = s1.upper()

    u2 = s2.upper()

    if u1 &lt; u2:

    if u1 &gt; u2:

忽略大小寫來比較兩個字元串,實際上就是先把字元串都變成大寫(或者都變成小寫),再比較。

這樣,我們給sorted傳入上述比較函數,即可實作忽略大小寫的排序:

sorted(['bob', 'about', 'Zoo', 'Credit'], cmp_ignore_case)

['about', 'bob', 'Credit', 'Zoo']

從上述例子可以看出,高階函數的抽象能力是非常強大的,而且,核心代碼可以保持得非常簡潔。

2.      匿名函數

顧名思義---&gt; 沒有名字的函數

形式1:

def sum(x, y):

    return x+y

print (sum(4, 5))

形式2:

m = lambda x,y:x+y

print (m(4, 5))

形式1 和 形式2 結果一樣

補充學習網址:https://www.liaoxuefeng.com/wiki/001374738125095c955c1e6d8bb493182103fac9270762a000/001386819873910807d8c322ca74d269c9f80f747330a52000

本文轉自 聽丶飛鳥說 51CTO部落格,原文連結:http://blog.51cto.com/286577399/1978530