1. 程式人生 > >Python開發【第十三篇】高階函式、遞迴函式、閉包

Python開發【第十三篇】高階函式、遞迴函式、閉包

函數語言程式設計是指用一系列函式解決問題
好處:用每個函式完成每個細小的功能,一系列函式任意組合能夠解決大問題
函式僅僅接收輸入併產生輸出,不包含任何能影響輸出的內部狀態

函式之間的可重入性

當一個函式的輸入實參一定,結果也必須一定的函式為可重入函式

例子:

#可重入函式
def myadd(x,y):
    return x+y
#不可重入函式
s = 0
def myadd2(x,y):
    global s
    s+= x+y
    return s

高階函式

  • map
  • filter
  • sorted

什麼是高階函式

​ 滿足下列條件中個任意一個的函式就是高階函式

​ 條件一:函式接收一個或多個函式中用引數傳入

​ 條件二:函式返回一個函式

map函式

​ map(func,*iterable)

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

例子:

對於list[1,2,3,4,5,6,7,8,9]

如果希望把list的每個元素都做平方,就可以用map()函式

因此,我們只需要傳入函式f(x)==x*x,就可以利用mnap()函式完成這個計算

def f(x):
    return x*x
print(map(f,[1,2,3,4,5,6,7,8,9]))
輸出結果:
[1.4.9.10.25.36.49.64.81]
注意:map函式是不改變原有的list的,而是生成一個新的list

map()函式是python內建的高階函式,對傳入的list的每一個元素進行對映,返回一個新的對映之後的list

python3中,map函式返回的是一個map物件,需要list(map(fun,itor))來將對映之後的map物件轉換成列表

map(func, *iterable) 返回一個可迭代物件,此可迭代
物件用函式 func對可迭代物件iterable中的每一個
元素作用引數計算後得一結果,當最短的一個可迭代對
象不再提供資料時可迭代物件生成資料結束

def mypower2(x, y):
    return x ** y

for x in map(mypower2,[1,2,3,4],[4,3,2,1]):
    print(x)
# 看懂下面程式在做什麼:
for x in map(pow, [1,2,3,4], [4,3,2,1],
             range(5, 10)):
    print(x)

filtert函式

filter(function,iterable)返回一個可迭代物件

​ 此可迭代物件將iterable提供的資料用函式function進行篩選

​ function將對iterable中的每個元素求值

​ 返回False將此資料丟棄,返回True則保留

示例:

def isood(x):
    return x % 2 == 1

列印0~10之間的所有奇數

for x in filter(isood,range(11)):
    print(X)
for x in filter(lambda x:x%2,range(11)):
    print(X)
L  = [x for x in filter(isood,range(11))]

sorted函式

作用:

將原可迭代物件提供的資料進行排序,生成排序後的列表

格式說明:

sorted(iterable,key=None,reverse=False)

返回一個新的包含所有可迭代物件中資料的列表,新的列表是排序過的列表

引數說明:

  • iterable —–>可迭代物件
  • key———>函式是用來提供一個值,這個值將作為排序的依據
  • reverse—–>標誌用來設定是否降序排序(預設為升序)

示例:

L = [5,-2,-4,0,3,1]
L2 = sorted(L)
k3 = sorted(L,keys=abs)
names= ['Tom','Jerry','Spike','Tyke']
sorted(names)
sorted(names,key=len,reverse=True)

遞迴函式

​ 什麼叫遞迴函式?

​ 函式直接或者間接的呼叫自身

示例:

#函式直接呼叫自身
def f():
    f()#呼叫自己
#函式間接呼叫自身
def fa():
    fb()
 def fb():
    fa()
 fa()

遞迴說明:

  • 遞迴一定要充值遞迴的成熟,當符合某一條件時要終止遞迴呼叫,幾乎所有的遞迴都能用while迴圈來代替

    優點:遞迴可以把問題簡單化,讓思路清晰,程式碼簡潔

    缺點:遞迴因系統環境影響大,當遞迴深度太大時,可以得到不可預知的結果

  • 遞迴函式的執行分為兩個階段

  • 遞推階段:呼叫進入函式內部

  • 迴歸階段:返回結果,得到最終結果

閉包

什麼是閉包?

  • 閉包是指引用了次函式外部變數的函式
    • (外部變數指:外部巢狀函式作用域內的變數)

閉包必須滿足三個條件

  • 必須有一個內嵌函式
  • 內嵌函式必須引用外部函式的變數
  • 外部函式返回值 必須為內嵌函式

注意:

由於閉包會使函式中的變數都儲存在記憶體中,計算機的記憶體消耗比較大,所以不能濫用閉包

示例

# 此示例示意閉包的定義及呼叫
def make_power(y):
    def fn(x):  # fn繫結一個閉包函式
        return x ** y
    return fn

pow2 = make_power(2)  # pow2繫結一個閉包函式
print("5的平方是:", pow2(5))

pow3 = make_power(3)
print("6的立方是:", pow3(6))

fp = make_power(100)
fp = make_power(10000)

閉包測試題:
試看下列程式的執行結果是什麼?

  def get_funs(n):
      L = []
      for i in range(n):
          L.append(lambda x: x * i)
      return L

  funs = get_funs(4)
  print(funs[0](10))  # 30
  print(funs[1](10))  # 30
  print(funs[2](10))  # 30
  print(funs[3](10))  # 30