歡迎光臨
我們一直在努力

我和Python的Py交易》》》》》》函式

文章摘要: have_name() # 用函式名呼叫函式 have_name函式名是指被封裝的程式碼呼叫函式時傳給函式的引數

一 函式是什麼?  是數學中的函式?

Python中 函式是指將一組語句的集合通過一個名字 (函式名) 封裝起來的一段程式碼。(所以這裏的函式是 subroutine子程式

那要函式幹嘛。不都是程式碼嗎?只不過函式是通過一個名字被封裝起來的一段程式碼。 有名字就就了不起啊!!!

對啊,有名字就是了不起啊,函式可以通過 函式名來呼叫 被其封裝起來的程式碼。

可以理解為是一個 變數 函式名 )指向的一段程式碼。這個變數( 函式名 )只是一段 沒有執行 的程式碼, 變數()函式名() )是表示 執行 這段程式碼

函式的作用

1.程式碼重用

例如:一段用來求兩數之和的程式碼通過一個函式名封裝成 一個函式每當需要 求和功能時就不用在把這段程式碼敲出來了,直接用函式名來 呼叫 這段程式碼

這樣這一段求被封裝成函式的求和程式碼就被 重複的使用 了很多次。(還省了你敲程式碼的時間)

2.保持一致性

每一個呼叫的函式都是同一個,程式碼都都是一樣的。

3.易擴充套件性

因為函式保持一致性,所有修改函式,為函式新增新功能時,只要修改一次,所有呼叫的該函式都會跟著變。

 二 建個函式玩玩

Python 定義函式使用 def 關鍵字( Definition 定義

def 函式名(引數列表):
    函式主體(被封裝起來的一段程式碼)

def have_name():
    print('有名字就是了不起!')
have_name()  # 用函式名呼叫函式  have_name函式名是指被封裝的程式碼,have_name()代表是執行這段程式碼。

函式名的命名規則:

  • 函式名必須以下劃線或字母開頭,可以包含任意字母、數字或下劃線的組合。不能使用任何的標點符號;
  • 函式名是區分大小寫的。
  • 函式名不能是保留字。

想要寫出高質量的程式碼,規範的命名是必不可少的。期待吧,少年,我會開單章隨筆來,叨叨這個命名的。

形參和實參

形參 形式上的引數,是應函式的 需求 虛擬出變數。當呼叫這個函式時,就會傳一個引數( 實參 )給形參,這樣虛擬的變數就變真實了( 實參個數,型別應與實參一一對應 );

實參 :實際引數,呼叫函式時傳給函式的引數, 可以是常量,變數,表示式,函式,傳給形參

打個比喻來形象的說明形參和實參的關係,在數學的函式 F(X)=X+1 中,X就是形參( 這個時候X不代表任何具體的值 ),而當把X=1帶人這個F(X)函式時,1就是實參。

區別 :形參是虛擬的,不佔用記憶體空間,形參變數只有在被呼叫時才分配記憶體單元,實參是一個變數,佔用記憶體空間。

def tow_sum(a,b):  #這個裡的a和b是沒有分配記憶體空間的
    c=a+b          #這裏的a和b是分配了記憶體空間的
    print(c)

tow_sum(1,2)       # 1和2 是實參為其分配了記憶體空間

三 和函式形參的促膝長談

函式的形參可以是 各種資料(數字,字串,元組,列表,字典等),函式名等……

函式形參(引數)

  • 關鍵字引數
  • 預設引數
  • 非關鍵字可變長引數(元組)
  • 關鍵字可變長引數(字典)

關鍵字引數 標準呼叫 時指定引數的名稱,且與函式宣告時的引數名稱 順序一致 。使用 關鍵字呼叫 引數允許函式呼叫時引數的順序與宣告時 不一致 ,僅根據引數的指定進行賦值。

def gu(a,b):
    if a==1:
        print('鐘鼓饌玉不足貴,但願長醉不復醒。')
    if b==2:
        print('古來聖賢皆寂寞,惟有飲者留其名。')

# 標準呼叫
gu(1,1)
#鐘鼓饌玉不足貴,但願長醉不復醒。

# 關鍵字呼叫(可以不按順序)
gu(b=2,a=1)
# 鐘鼓饌玉不足貴,但願長醉不復醒。
# 古來聖賢皆寂寞,惟有飲者留其名。

預設引數 : 在函式宣告時,指定形參的預設值,呼叫時可不傳入改引數( 使用預設值 )。

def gu(a=1,b=0):
    if a==1:
        print('鐘鼓饌玉不足貴,但願長醉不復醒。')
    if b==2:
        print('古來聖賢皆寂寞,惟有飲者留其名。')

gu()
#鐘鼓饌玉不足貴,但願長醉不復醒。

gu(2,2)
#古來聖賢皆寂寞,惟有飲者留其名。

gu(b=2,a=0)
#古來聖賢皆寂寞,惟有飲者留其名。

非關鍵字可變長引數(元組) :「 非關鍵字 」「 可變長 」顧名思義是允許在呼叫時傳入多個「 非關鍵字 」引數,python會將這些多出來的 引數放入一個元組中

def gu(*s):
    print(type(s))
    print(s)

gu(1,'鐘鼓饌玉不足貴,但願長醉不復醒。',2,'古來聖賢皆寂寞,惟有飲者留其名。')   #可變長,愛有幾個引數就調幾個引數

#   元組
# (1, '鐘鼓饌玉不足貴,但願長醉不復醒。', 2, '古來聖賢皆寂寞,惟有飲者留其名。')

關鍵字可變長引數(字典) :「 關鍵字 」「 可變長 」顧名思義是允許在呼叫時傳入多個「關鍵字」引數,python會將這些多出來的 <引數名, 引數值>放入一個字典中

def gu(**s):
    print(type(s))
    print(s)
    print(s['a'])
    print(s['b'])

gu(a= "鐘鼓饌玉不足貴,但願長醉不復醒。", b= '古來聖賢皆寂寞,惟有飲者留其名。')  #可變長,愛有幾個引數就調幾個引數

#   字典
# {'a': '鐘鼓饌玉不足貴,但願長醉不復醒。', 'b': '古來聖賢皆寂寞,惟有飲者留其名。'}
# 鐘鼓饌玉不足貴,但願長醉不復醒。
# 古來聖賢皆寂寞,惟有飲者留其名。

需要注意的是當它們 混用時 ,關鍵字變數引數應該為函式定義的最後一個引數,帶** 。 呼叫函式時引數的輸入也有不同的方式。

def gu(a,b,*c,**d):
    print(a)
    print(b)
    print(c)
    print(d)
gu(1,2,3,f=7,g=8)

# 1
# 2
# (3,)
# {'f': 7, 'g': 8}

def gu(a,b,*c,**d):
    print(a)
    print(b)
    print(c)
    print(d)
gu(1,2,*('鐘鼓饌玉不足貴,但願長醉不復醒',),**{'t': '鐘鼓饌玉不足貴,但願長醉不復醒。', 'f': '古來聖賢皆寂寞,惟有飲者留其名。'})

# 1
# 2
# ('鐘鼓饌玉不足貴,但願長醉不復醒',)
# {'t': '鐘鼓饌玉不足貴,但願長醉不復醒。', 'f': '古來聖賢皆寂寞,惟有飲者留其名。'}

四 給回扣的返回值

要想獲取函式的執行結果,就可以用return語句把結果返回

return返回值可以是 各種資料(數字,字串,元組,列表,字典等),函式名等……

注意:

  1. 函式在執行過程中只要遇到return語句,就會停止執行並返回結果,so 也可以理解為 return 語句代表著函式的結束
  2. 如果未在函式中指定return,那這個函式的返回值為None,Python會自動給函式加 return None

  3. return多個物件,直譯器會把這多個物件 組裝成一個元組 作為 一個整體 結果輸出。
def gu(a):
   return a

b = gu('古來聖賢皆寂寞,惟有飲者留其名。')
print(b)

五 就是比你高的高階函式

高階函式是 至少滿足下列一個條件的函式 :

  • 接受一個或多個函式作為輸入( 引數
  • 輸出一個函式( return 返回值

遞迴函式,修飾器也都是高階函式的運用

六 鞭長莫及的作用域

作用域研究的是資料的 適用範圍

就像地球的重力加速度g在火星上就不適用。

def globe():
    g = 9.8

def mars():
    g = 3.71

上述程式碼中兩個g是 毫無關係的 ,因為 它們的作用域不同一個函式就是一個作用域 。在globe()中的g的只在globe函式中適用,另一個g也是是如此。

這只是作用域的小小體現, 作用域不只在函式中有,在類,包中都有體現 。還有如何去呼叫,修改不同作用域裡的資料

這些都會開單章來嘮叨一下。

七 自娛自樂的遞迴

定義:一個函式在內部呼叫自身本身,這個函式就是遞迴函式。

說白了就是自己和自己玩(單身人士都懂的)

注意:

1. 必須有一個明確的 結束條件 (不可自娛自樂太久要有個度)

2. 每次進入更深一層遞迴時,問題規模相比上次遞迴都應有所減少  (每自娛自樂一次總得緩解一下單身狗的苦)

3. 遞迴效率不高,遞迴層次 過多 會導致棧溢位。 (自娛自樂多了傷身)

註釋:(在計算機中,函式呼叫是通過棧(stack)這種數據結構實現的,每當進入一個函式呼叫,棧就會加一層棧幀,每當函式執行結束,棧就會減一層棧幀。由於棧的大小不是無限的,所以,遞迴呼叫的次數過多,會導致棧溢位。)

階乘的計算

# **********迴圈*********
def factorial(n):
    result = n
    for i in range(1, n):
        result *= i

    return result

print(factorial(3))

# **********遞迴*********
def factorial_new(n):
    if n == 1:  # 遞迴結束條件
        return 1
    result=factorial_new(n - 1)
    result = n * result
    return result

a = factorial_new(3)
print(a)

遞迴函式是定義簡單,邏輯清晰。理論上,所有的遞迴函式都可以寫 成迴圈的方式 ,但迴圈的邏輯不如遞迴清晰。

八 良心的內建函式

內建函式就是Python提供的,可以直接使用的函式, 所以 內建函式一般都是使用頻繁的函式。

以後會仔細說一下有哪些內建函式

九 無副作用的函數語言程式設計

常見的程式設計正規化有 指令式程式設計函數語言程式設計

指令式程式設計 :是面向計算機硬體的抽象,有變數(對應著儲存單元),賦值語句(獲取,儲存指令),表示式(記憶體引用和算術運算)和控制語句(跳轉指令), 命令式程式就是一個馮諾依曼機的按照打孔紙帶執行指令。

函數語言程式設計 是面向數學的抽象, 他將計算機運算看做是數學中函式的計算,並且避免了狀態以及變數的概念, 一句話, 函式式程式就是一個表示式

程序導向程式設計,物件導向程式設計 都是 指令式程式設計

函數語言程式設計的本質

函數語言程式設計中的 函式 這個術語不是指計算機中的函式,而是指 數學中的函式 ,即 自變數的對映 。也就是說一個函式的值僅決定於 函式引數的值 ,不依賴其他狀態。

我們要做的是把函式傳來傳去,而這個,說成術語,我們把他叫做高階函式

函式是基本單位,他幾乎被用作一切,包括最簡單的計算,甚至連變數都被計算所取代。

變數只是一個名稱,而不是一個儲存單元, 這是函數語言程式設計與傳統的指令式程式設計最典型的不同之處

函數語言程式設計取消了 賦值模型 ,則使 數學模型與程式設計模型完美地達成了統一

函數語言程式設計 關心 資料的對映 ,指令式程式設計 關心 解決問題的步驟。

#計算列表中數的平均值
#***********指令式程式設計***************
number = [0,1, 2, 3, 4, 5, 6, 7, 8, 9]
count = 0
add = 0

for i in range(len(number)):
        count += 1          # 第一步 計數
        add+= number[i]    # 第二步 求和

if count > 0:
    average = add/ count   # 第三步 計算平均數

print(average)


#***********函數語言程式設計***************
number = [0,1, 2, 3, 4, 5, 6, 7, 8, 9]
average = sum(number) / len(number)
print(average)

歡迎評論,番茄,雞蛋都砸過來吧!!!

未經允許不得轉載:頭條楓林網 » 我和Python的Py交易》》》》》》函式