python基礎(函式引數魔法,位置引數)

2021-09-11 09:02:53 字數 3227 閱讀 9032

1.值從**來

定義函式時,你可能心存疑慮:引數的值是怎麼來的呢?

編寫函式旨在為當前程式(甚至其他程式)提供服務,你的職責是確保它在提供的引數正確時完成任務,並在引數不對時以顯而易見的方式失敗。(為此,通常使用斷言或異常。)

在def語句中,位於函式名後面的變數通常稱為形參,而呼叫函式時提供的值稱為實參。

2.我能修改引數嗎

函式通過引數獲得了一系列的值,能對其進行修改嗎?如果這樣做,結果將如何?引數不過是變數而已,行為與你預期的完全相同。在函式內部給引數賦值對外部沒有任何影響。

>>> def try_to_change(n): 

...          n = 'mr. gumby' 

... 

>>> name = 'mrs. entity' 

>>> try_to_change(name) 

>>> name 

'mrs. entity' 

在try_to_change內,將新值賦給了引數n,但如你所見,這對變數name沒有影響。說到底,這是乙個完全不同的變數。傳遞並修改引數的效果類似於下面這樣:

>>> name = 'mrs. entity' 

>>> n = name # 與傳遞引數的效果幾乎相同

>>> n = 'mr. gumby' # 這是在函式內進行的

>>> name 

'mrs. entity'

這裡的結果顯而易見:變數n變了,但變數name沒變。同樣,在函式內部重新關聯引數(即給它賦值)時,函式外部的變數不受影響。

引數儲存在區域性作用域內。

字串(以及數和元組)是不可變的(immutable),這意味著你不能修改它們(即只能替換為新值)。因此這些型別作為引數沒什麼可說的。但如果引數為可變的資料結構(如列表)呢?

>>> def change(n): 

...         n[0] = 'mr. gumby' 

... 

>>> names = ['mrs. entity', 'mrs. thing'] 

>>> change(names) 

>>> names 

['mr. gumby', 'mrs. thing'] 

在這個示例中,也在函式內修改了引數,但這個示例與前乙個示例之間存在乙個重要的不同。在前乙個示例中,只是給區域性變數賦了新值,而在這個示例中,修改了變數關聯到的列表。這很奇怪吧?其實不那麼奇怪。下面再這樣做一次,但這次不使用函式呼叫。

>>> names = ['mrs. entity', 'mrs. thing'] 

>>> n = names # 再次假裝傳遞名字作為引數

>>> n[0] = 'mr. gumby' # 修改列表

>>> names 

['mr. gumby', 'mrs. thing']

這樣的情況你早就見過。將同乙個列表賦給兩個變數時,這兩個變數將同時指向這個列表。就這麼簡單。要避免這樣的結果,必須建立列表的副本。對序列執行切片操作時,返回的切片都是副本。因此,如果你建立覆蓋整個列表的切片,得到的將是列表的副本。

>>>

names

= ['mrs. entity', 'mrs. thing'] 

>>>

n= names

[:] 

現在n和names包含兩個相等但不同的列表。

>>>

nis

names

false 

>>>

n== names 

true 

現在如果(像在函式change中那樣)修改n,將不會影響names。

>>> n[0] = 'mr. gumby' 

>>> n 

['mr. gumby', 'mrs. thing'] 

>>> names 

['mrs. entity', 'mrs. thing'] 

下面來嘗試結合使用這種技巧和函式change。

>>> change(names[:]) 

>>> names 

['mrs. entity', 'mrs. thing'] 

注意到引數n包含的是副本,因此原始列表是安全的。

函式內的區域性名稱(包括引數)會與函式外的名稱(即全域性名稱)衝突嗎?答案是不會。

下面來嘗試執行該程式:

>>> mynames = {} 

>>> init(mynames) 

>>> store(mynames, 'magnus lie hetland') 

>>> lookup(mynames, 'middle', 'lie') 

['magnus lie hetland'] 

看起來能正確地執行。下面再來嘗試幾次。

>>> store(mynames, 'robin hood') 

>>> store(mynames, 'robin locksley') 

>>> lookup(mynames, 'first', 'robin') 

['robin hood', 'robin locksley'] 

>>> store(mynames, 'mr. gumby') 

>>> lookup(mynames, 'middle', '') 

['robin hood', 'robin locksley', 'mr. gumby']

如你所見,如果多個人的名字、中間名或姓相同,可同時獲取這些人員。

2). 如果引數是不可變的

在有些語言(如c++、pascal和ada)中,經常需要給引數賦值並讓這種修改影響函式外部的變數。在python中,沒法直接這樣做,只能修改引數物件本身。但如果引數是不可變的(如數)呢?不好意思,沒辦法。在這種情況下,應從函式返回所有需要的值(如果需要返回多個值,就以元組的方式返回它們)。例如,可以像下面這樣編寫將變數的值加1的函式:

>>> definc(x): return x + 1 

... 

>>> foo = 10 

>>> foo = inc(foo) 

>>> foo 

11 如果一定要修改引數,可玩點花樣,比如將值放在列表中,如下所示:

>>> def inc(x): x[0] = x[0] + 1 

... 

>>> foo = [10] 

>>> inc(foo) 

>>> foo 

[11] 

但更清晰的解決方案是返回修改後的值。

python基礎常用的魔法函式

類中的初始化函式,可以顯式顯示即子呼叫類的時候以進行了函式的初始化。通過vars函式獲知顯示宣告的屬性,但是隱式的就無法獲知了,直接列印物件的實現方法,str 是被print函式呼叫的,一般都是return乙個什麼東西,這個東西應該是以字串的形式表現的。如果不是要用str 函式轉換,我們可以直接pr...

Python基礎 函式 函式引數

引數就是傳入的值 示例 usr bin env python3 coding utf 8 函式的引數和預設引數 defregist name,age,city shenzhen print name name print age age print city city 執行結果 d pythonpr...

python魔法函式

python中魔法函式簡單上來說就是在構建某個類的時候,給類定義一些初始的方法,來實現類物件的某些屬性或者方法而準備。其形式如下,下雙劃線開頭雙劃線結尾 初始化乙個學生class class student def init self,students list self.students list...