您好,登錄后才能下訂單哦!
Python中怎么對(duì)函數(shù)參數(shù)進(jìn)行操作,相信很多沒有經(jīng)驗(yàn)的人對(duì)此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個(gè)問題。
形參和實(shí)參
不止 Python,幾乎所有的編程語言都會(huì)涉及兩個(gè)術(shù)語:parameter 和 argument。那么,它們之間究竟有什么區(qū)別呢?
parameter 是指函數(shù)定義中的參數(shù),而 argument 指的是函數(shù)調(diào)用時(shí)的實(shí)際參數(shù)。
簡略描述:parameter = 形參(formal parameter), argument = 實(shí)參(actual parameter)。
例如,定義一個(gè)簡單的函數(shù):
>>> def greet(param1, param2): ... pass ... >>> >>> greet('Hello', 'Python')
其中,param1 和 param2 是函數(shù)的形參,而在函數(shù) greet()
被調(diào)用時(shí),傳入的('Hello' 和 'Python')則是實(shí)參。
固定數(shù)量參數(shù)的函數(shù)
到目前為止,關(guān)于函數(shù),我們介紹的都是固定數(shù)量的參數(shù)。來看一個(gè)簡單的示例:
>>> def greet(say, msg): ... print(say, msg) ... >>> >>> greet('Hello', 'Python') Hello Python
這里,函數(shù) greet()
有兩個(gè)參數(shù),用兩個(gè)參數(shù)調(diào)用這個(gè)函數(shù),運(yùn)行得很順利,不會(huì)有任何錯(cuò)誤。
倘若,參數(shù)的個(gè)數(shù)不匹配,會(huì)發(fā)生什么?
>>> greet() # 沒有參數(shù) ... TypeError: greet() missing 2 required positional arguments: 'say' and 'msg' >>> >>> greet('Hi') # 只有一個(gè)參數(shù) ... TypeError: greet() missing 1 required positional argument: 'msg'
顯然,解釋器會(huì)發(fā)牢騷。但是,對(duì) Python 來說,要解決這個(gè)問題簡直是易如反掌,繼續(xù)往下看!
默認(rèn)參數(shù)
定義函數(shù)時(shí),可以使用賦值運(yùn)算符(=)為參數(shù)指定一個(gè)默認(rèn)值。
注意: 如果參數(shù)沒有默認(rèn)值,在調(diào)用時(shí)必需為其指定一個(gè)值;如果參數(shù)有默認(rèn)值,那么在調(diào)用時(shí)值是可選的,如果為其提供了一個(gè)值,將會(huì)覆蓋默認(rèn)值。
>>> def greet(say, name = 'James', msg = 'I am your biggest fan!'): ... print(say, ',', name, ',', msg) ... >>> greet('Hi') # 只提供強(qiáng)制性的參數(shù) Hi , James , I am your biggest fan! >>> >>> greet('Hi', 'Kobe') # 給出一個(gè)可選參數(shù) Hi , Kobe , I am your biggest fan! >>> >>> greet('Hi', 'Kobe', 'I want to challenge you!') # 給出所有參數(shù) Hi , Kobe , I want to challenge you!
由于 say 沒有默認(rèn)值,所以必須指定;name、msg 有默認(rèn)值,所以值是可選的。
函數(shù)中的所有參數(shù)都可以有默認(rèn)值,但是,一旦存在一個(gè)默認(rèn)參數(shù),其右側(cè)的所有參數(shù)也必須有默認(rèn)值。也就是說,非默認(rèn)參數(shù)不能在默認(rèn)參數(shù)之后。
例如,將上面的函數(shù)定義為:
def greet(name = 'James', say):
就會(huì)引發(fā)錯(cuò)誤:
SyntaxError: non-default argument follows default argument
關(guān)鍵字參數(shù)
當(dāng)使用某些值調(diào)用函數(shù)時(shí),這些值將根據(jù)其位置分配給參數(shù)。
例如,在上述函數(shù) greet()
中,當(dāng)使用 greet('Hi', 'Kobe')
調(diào)用它時(shí),'Hi' 被賦值給參數(shù) say,同樣地,'Kobe' 被賦值給 name。
Python 允許使用 kwarg = value
格式的關(guān)鍵字參數(shù)調(diào)用函數(shù):
>>> def greet(say, name = 'James'): ... print(say, ',', name) ... >>> >>> greet(say = 'Hi', name = 'Kobe') # 2 個(gè)關(guān)鍵字參數(shù) Hi , Kobe >>> >>> greet(name = 'Kobe', say = 'Hi') # 2 個(gè)關(guān)鍵字參數(shù)(次序顛倒) Hi , Kobe >>> >>> greet('Hi', name = 'Kobe') # 位置參數(shù)與關(guān)鍵字參數(shù)混合使用 Hi , Kobe
當(dāng)以這種方式調(diào)用函數(shù)時(shí),關(guān)鍵字參數(shù)必須在位置參數(shù)之后,所有傳遞的關(guān)鍵字參數(shù)都必須與函數(shù)接受的某個(gè)參數(shù)匹配,并且它們的順序不重要。
例如,像下面這樣調(diào)用,會(huì)引發(fā)錯(cuò)誤:
>>> greet(name = 'Kobe', 'Hi') # 關(guān)鍵字參數(shù)在位置參數(shù)之前 ... SyntaxError: positional argument follows keyword argument >>> >>> greet('Hi', na = 'Kobe') # na 不匹配 ... TypeError: greet() got an unexpected keyword argument 'na'
可變參數(shù)
可變參數(shù)也被稱為不定長參數(shù),顧名思義,就是傳入的參數(shù)個(gè)數(shù)是可變的,可以是任意個(gè)(0、1、2 … N)。
要定義可變參數(shù),僅需在參數(shù)名之前添加一個(gè)星號(hào)(*
)。在函數(shù)內(nèi)部,這些參數(shù)被包裝為一個(gè) tuple
。
注意: 此 * 非彼 *,不要誤認(rèn)為是 C/C++ 中的指針。
>>> def greet(*names): ... print(names) ... >>> >>> greet() # 沒有參數(shù),返回空元組 () >>> >>> greet('Jordan', 'James', 'Kobe') ('Jordan', 'James', 'Kobe')
有時(shí),必須在函數(shù)定義中使用位置參數(shù)以及可變參數(shù),但位置參數(shù)始終必須在可變參數(shù)之前。
>>> def greet(say, *names): ... print(say, names) ... >>> >>> greet('Hi') Hi () >>> >>> greet('Hi', 'Jordan', 'James', 'Kobe') Hi ('Jordan', 'James', 'Kobe')
通常情況下,可變參數(shù)會(huì)出現(xiàn)在形參列表的最后,因?yàn)樗鼈儠?huì)把傳遞給函數(shù)的所有剩余輸入?yún)?shù)都收集起來??勺儏?shù)之后出現(xiàn)的任何形參都是“強(qiáng)制關(guān)鍵字”參數(shù),這意味著,它們只能被用作關(guān)鍵字參數(shù),而不能是位置參數(shù)。
>>> def greet(*names, sep = ','): ... return sep.join(names) ... >>> >>> greet('Jordan', 'James', 'Kobe') 'Jordan,James,Kobe' >>> >>> greet('Jordan', 'James', 'Kobe', sep = '/') # 被用作關(guān)鍵字參數(shù) 'Jordan/James/Kobe' >>> >>> greet('Jordan', 'James', 'Kobe', '/') # 被用作位置參數(shù) 'Jordan,James,Kobe,/'
任意關(guān)鍵字參數(shù)
還有一種機(jī)制,用于任意數(shù)量的關(guān)鍵字參數(shù)。為了做到這一點(diǎn),使用雙星號(hào)(**
):
>>> def greet(**all_star): ... print(all_star) ... >>> greet() # 沒有參數(shù),返回空字典 {} >>> >>> greet(name = 'James', age = 18) {'name': 'James', 'age': 18}
當(dāng)最后一個(gè)形式為 **msgs
的形參出現(xiàn)時(shí),它將收到一個(gè)字典,其中包含所有關(guān)鍵字參數(shù),除了與形參對(duì)應(yīng)的關(guān)鍵字參數(shù)之外。還可以與 *names
的形參相結(jié)合(*names
必須出現(xiàn)在 **msgs
之前)。
例如,定義一個(gè)這樣的函數(shù):
>>> def greet(say, *names, **msgs): ... print('--', say) ... for name in names: ... print(name) ... print('-' * 40) ... keys = sorted(msgs.keys()) ... for key in keys: ... print(key, ':', msgs[key]) ... >>> >>> greet('Hi', 'Jordan', 'James', 'Kobe', msg = 'I want to challenge you!', challenger = 'Waleon') -- Hi Jordan James Kobe ---------------------------------------- challenger : Waleon msg : I want to challenge you!
注意: 在打印內(nèi)容之前,通過對(duì) msgs 字典的 keys()
方法的結(jié)果進(jìn)行排序來創(chuàng)建關(guān)鍵字參數(shù)名稱列表。如果沒有這樣做,則打印參數(shù)的順序是未定義的。
對(duì)參數(shù)進(jìn)行解包
正如“可變參數(shù)”那樣,也可在函數(shù)調(diào)用中使用 *
操作符。只不過在這種情況下,與在函數(shù)定義中 *
的語義相反,參數(shù)將被解包而不是打包。
>>> def greet(name, age): ... print(name, age) ... >>> >>> t = ('James', 18) >>> greet(*t) James 18
還有一種方式,幾乎沒有必要提到,這里也羅嗦一下:
>>> greet(t[0], t[1]) James 18
與解包相比,這種調(diào)用方式顯然不舒適。另外,在一般情況下,調(diào)用 greet(t[0], t[1])
幾乎是徒勞的,因?yàn)殚L度是未知的。“未知”的意思是:長度只在運(yùn)行時(shí)才知道,而不是在編寫腳本時(shí)就知道。
同樣地,字典也可以用 **
操作符傳遞關(guān)鍵字參數(shù):
>>> def greet(name, age = 18): ... print(name, age) ... >>> >>> d = {'name':'James', 'age':32} >>> greet(**d) James 32
Python獲取函數(shù)參數(shù)個(gè)數(shù):
Python2.7寫法:
# -*- coding:utf-8 -*- #! python2 def abc(a,b,c): print a,b yy=abc.func_code.co_argcount print yy
輸出結(jié)果為
3
python3.6寫法
# -*- coding:utf-8 -*- #! python3 def abc(a,b,c): print(a,b) a=abc.__code__.co_argcount print(a)
輸出結(jié)果為
3
使用場(chǎng)景:
比如在REST規(guī)范的代碼中,request數(shù)據(jù)格式檢驗(yàn),判斷攜帶參數(shù)個(gè)數(shù)是否符合該函數(shù)所需參數(shù)的個(gè)數(shù),不是就可以return error了
看完上述內(nèi)容,你們掌握Python中怎么對(duì)函數(shù)參數(shù)進(jìn)行操作的方法了嗎?如果還想學(xué)到更多技能或想了解更多相關(guān)內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道,感謝各位的閱讀!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。