剛學用python的時候,特別是看一些庫的原始碼時,經常會看到func(*args, **kwargs)這樣的函式定義,這個*和**讓人有點費解。其實只要把函式引數定義搞清楚了,就不難理解了。
先說說函式定義,我們都知道,下面的**定義了乙個函式funca
def funca():
pass
顯然,函式funca沒有引數(同時啥也不幹:d)。
下面這個函式funcb就有兩個引數了,
def funcb(a, b):
print a
print b
呼叫的時候,我們需要使用函式名,加上圓括號擴起來的引數列表,比如 funcb(100, 99),執行結果是:
10099
很明顯,引數的順序和個數要和函式定義中一致,如果執行funcb(100),python會報錯的:
typeerror: funcb() takes exactly 2 arguments (1 given)
我們可以在函式定義中使用引數預設值,比如
def funcc(a, b=0):
print a
print b
在函式funcc的定義中,引數b有預設值,是乙個可選引數,如果我們呼叫funcc(100),b會自動賦值為0。
ok,目前為止,我們要定義乙個函式的時候,必須要預先定義這個函式需要多少個引數(或者說可以接受多少個引數)。一般情況下這是沒問題的,但是也有在定義函式的時候,不能知道引數個數的情況(想一想c語言裡的printf函式),在python裡,帶*的引數就是用來接受可變數量引數的。看乙個例子
def funcd(a, b, *c):
print a
print b
print "length of c is: %d " % len(c)
print c
呼叫funcd(1, 2, 3, 4, 5, 6)結果是12
length of c is: 4
(3, 4, 5, 6)
我們看到,前面兩個引數被a、b接受了,剩下的4個引數,全部被c接受了,c在這裡是乙個tuple。我們在呼叫funcd的時候,至少要傳遞2個引數,2個以上的引數,都放到c裡了,如果只有兩個引數,那麼c就是乙個empty tuple。
好了,一顆星我們弄清楚了,下面輪到兩顆星。
上面的例子裡,呼叫函式的時候,傳遞的引數都是根據位置來跟函式定義裡的參數列匹配的,比如funcb(100, 99)和funcb(99, 100)的執行結果是不一樣的。在python裡,還支援一種用關鍵字引數(keyword argument)呼叫函式的辦法,也就是在呼叫函式的時候,明確指定引數值付給那個形參。比如還是上面的funcb(a, b),我們通過這兩種方式呼叫
funcb(a=100, b=99)
和funcb(b=99, a=100)
結果跟funcb(100, 99)都是一樣的,因為我們在使用關鍵字引數呼叫的時候,指定了把100賦值給a,99賦值給b。也就是說,關鍵字引數可以讓我們在呼叫函式的時候打亂引數傳遞的順序!
另外,在函式呼叫中,可以混合使用基於位置匹配的引數和關鍵字引數,前題是先給出固定位置的引數,比如
def funce(a, b, c):
print a
print b
print c
呼叫funce(100, 99, 98)和呼叫funce(100, c=98, b=99)的結果是一樣的。
好了,經過以上鋪墊,兩顆星總算可以出場了:
如果乙個函式定義中的最後乙個形參有 ** (雙星號)字首,所有正常形參之外的其他的關鍵字引數都將被放置在乙個字典中傳遞給函式,比如:
def funcf(a, **b):
print a
for x in b:
print x + ": " + str(b[x])
呼叫funcf(100, c='你好', b=200),執行結果
100c: 你好
b: 200
大家可以看到,b是乙個dict物件例項,它接受了關鍵字引數b和c。
常規引數,*引數及**引數可以同時使用,具體怎麼用?看看python reference manual吧,關於function definitions的那些章節。其實,笨想也能猜出來啊,o(∩_∩)o...
Python可變引數
在python函式中,還可以定義可變引數。顧名思義,可變引數就是傳入的引數個數是可變的,可以是1個 2個到任意個,還可以是0個。以數學題為例子,給定一組數字a,b,c 請計算a2 b2 c2 要定義出這個函式,我們必須確定輸入的引數。由於引數個數不確定,我們首先想到可以把a,b,c 作為乙個list...
python 可變引數
1.args可以使用陣列和元組 2.kwargs可以使用字典作為引數def t args p,args 把陣列 元組作為引數傳遞給 args param p param args return print p for a in args print a deft kw p,kwargs 把字典作為可...
python中的可變引數和不可變引數
知識點 python中,萬物皆物件。python中不存在所謂的傳值呼叫,一切傳遞的都是物件的引用,也可以認為是傳址。python在heap中分配的物件分成兩類 可變物件和不可變物件。所謂可變物件是指,物件的內容可變,而不可變物件是指物件內容不可變。不可變 immutable int 字串 strin...