pythonの関数の引数の動作についてまとめる.
3系も含む.
A. 関数を使うとき
番号 | Syntax | 機能 |
---|---|---|
1 | func(value) | 通常の呼び出し, 関数呼出と引数の位置が対 |
2 | func(name=value) | キーワードに対応して関数呼出 |
3 | func(*iterable) | iterableなものを展開して関数呼出 |
4 | func(**dict) | dictをkey, valueに展開して関数呼出(2の引数をdictにして渡す) |
B. 関数を定義するとき
番号 | Syntax | 機能 |
---|---|---|
1 | def func(name) | 通常の関数定義, 関数呼出と引数の位置が対 |
2 | def func(name=value) | 引数に初期値を設定する |
3 | def func(*name) | 引数をタプルにする |
4 | def func(**name) | 引数をdictionaryにする |
5 | def func(*arg, name) | nameだけは指定必要,3系のみ |
6 | def func(*, name=value) | 引数をすべて指定が必要なものにする, 3系のみ |
Bの5, 6について
5と6がわかりにくい
pythonの関数呼出では, name = value
として呼び出せるけれど, def func(name)
だけでは, 関数呼出側が, name = valueにするか, valueだけで渡すのか自由にできる. そうすると当然コードにばらつきが出てくる.
で, それを解消しようとして3系からそれを強制するsyntaxができた(たぶん).
5について
5 はname = value
を強制するものと, そうでないものを共存させることができる.
下記では, cだけ, name = valueの形式を強制する.
In [18]: def kwonly(a, *b ,c):
....: print(a, b, c)
....:
In [19]: kwonly(1,2,3)
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-19-763cbb52b1ed> in <module>()
----> 1 kwonly(1,2,3)
TypeError: kwonly() missing 1 required keyword-only argument: 'c'
# cはname = valueでしか値が渡せない
In [20]: kwonly(1, 2, c=3)
1 (2,) 3
6について
5とほぼ同じなんだけど, 全部をname = valueにして, かつデフォルト値も決めておきましょう, というもの. もちろんデフォルト値はなくてもよいです. デフォルト値もできますよ, という意味程度で.
In [21]: def kwonly2(*, b , c=3):
....: print(b,c)
....:
In [22]: kwonly2(1)
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-22-ace6c6f57de4> in <module>()
----> 1 kwonly2(1)
TypeError: kwonly2() takes 0 positional arguments but 1 was given
# そもそも1が引数として認識されていない
In [23]: kwonly2(b=1)
1 3
In [24]: kwonly2(b=1,2)
File "<ipython-input-24-6c15c1f279e8>", line 1
kwonly2(b=1,2)
^
SyntaxError: non-keyword arg after keyword arg
# cはname = valueでしか渡せない(もちろんbも)
In [25]: kwonly2(b=1,c=2)
1 2