この記事では、Pythonの引数の使い方を解説します。
引数を使うことで関数内やメソッド内で使用する値を外部から受け取ることができます。また、デフォルト値を設定したり位置専用にしたり色々なオプションが用意されています。
関数の使い方は以下の記事を参照してください。
それでは、引数の使い方を見ていきましょう!
引数の基本
引数は以下のように定義します。
def 関数名(引数1, 引数2, ..., 引数N):
関数定義時に使用する引数のことを「仮引数(parameter)」、関数呼び出し時に引き渡される値のことを「実引数(argument)」と呼ぶ
アノテーションで型を指定することもできる。
def func(arg1: int, arg2: str):
サンプル
引数で外部から値を受け取って出力してみます。
def intro(name: str, age: int):
print(f'名前: {name}, 年齢: {age}')
intro('田中太郎', 20)
実行結果
名前: 田中太郎, 年齢: 20
デフォルト値の指定
仮引数に=
で繋いで値を指定することでデフォルト値を定義することができます。
def func(arg: int = 1):
引数が複数ある場合、前の引数にだけ初期値を付けることはできない。以下のコードでは、SyntaxError
が発生する。
def func(name: str = 'noname', age: int):
後ろから前に付けることは可能です。
def func(name: str, age: int = 0):
def func(name: str = 'noname', age: int = 0):
デフォルト値を指定した引数は呼び出し時に省略することもできます。
def func(name: str = 'noname', age: int = 0):
print(f'name: {name}, age: {age}')
# 第二引数を省略
func('Mike')
# 第一引数を省略
func(age=20)
# 引数を省略
func()
実行結果
name: Mike, age: 0
name: noname, age: 20
name: noname, age: 0
ただし、デフォルト値を指定する際に注意しなければならないのがミュータブルなオブジェクトを使用する場合です。
デフォルト値は、関数が定義されたときに一度だけ生成されます。つまりは同じオブジェクトを使い回していることになります。
そうするとミュータブルなオブジェクトでは、前回の変更がそのまま残ってしまっているのでめちゃくちゃ使いづらいです。例えば、以下のような感じですね。
def func(datas: list = []):
datas.append(1)
print(datas)
func()
func()
実行結果
[1]
[1, 1]
ミュータブルなオブジェクトにデフォルト値を指定したい場合は、None
を用いるのが一般的です。例えば、以下のような感じです。
def func(datas: list = None):
if datas is None:
datas = []
datas.append(1)
print(datas)
func()
func()
実行結果
[1]
[1]
位置専用引数
仮引数として/(スラッシュ)
を記述するとそれよりも前の仮引数は全て位置専用引数となります。
def 関数名(引数, /):
なんらかの処理
サンプル
位置専用引数を定義した関数を「通常の呼び出し」と「キーワード呼び出し」で使ってみます。
def func(arg, /):
print(arg)
func(0)
func(arg=0)
実行結果
0
Traceback (most recent call last):
File "main.py", line 8, in <module>
func(arg=0)
TypeError: func() got some positional-only arguments passed as keyword arguments: 'arg'
使い所
辞書の可変長引数を受け取る関数でkeyと引数名が被ってしまった場合に、名前の衝突を避けることができます。
例えば以下のコードを見てください。
def func(name, **kwds):
print(name, kwds['name'])
person = {'name': 'Mike'}
func('John', **person)
このコードを実行するとname引数に複数の値が渡されTypeError
が発生します。しかし、以下のように位置専用引数にすることでこのエラーは回避できます。
# nameを位置専用に
def func(name, /, **kwds):
print(name, kwds['name'])
person = {'name': 'Mike'}
func('John', **person)
キーワード専用引数
仮引数として*(アスタリスク)
を記述するとそれよりも後ろの仮引数は全てキーワード専用引数となります。
def 関数名(*, arg):
なんらかの処理
サンプル
キーワード専用引数を定義した関数を「通常の呼び出し」と「キーワード呼び出し」で使ってみる。
def func(*, arg):
print(arg)
func(arg=0)
func(0)
実行結果
0
Traceback (most recent call last):
File "main.py", line 8, in <module>
func(0)
TypeError: func() takes 0 positional arguments but 1 was given
位置専用 + キーワード専用
1つの関数に位置専用とキーワード専用の引数を定義することができます。
def 関数名(位置専用, ..., /, 通常, ..., *, キーワード専用, ...):
なんらかの処理
サンプル
試しにどちらの引数も定義した関数を呼び出してみます。
def func(pos, /, nor, *, key):
print(pos, nor, key)
func('pos', 'nor', key='key')
# もちろんnor引数はキーワード呼び出しもできる
func('pos', nor='nor', key='key')
実行結果
pos nor key
pos nor key
任意引数リスト
仮引数名の先頭に*(アスタリスク)
を付けることで任意の個数の引数で呼び出せるようにでき、それ以降の引数をキーワード呼び出し専用にすることができます。
def 関数名(*引数):
なんらかの処理
サンプル
以下のサンプルでは引数で受け取った複数の文字列を連結して任意の文字数に分割して返す関数を定義しています。
def func(*s, step=1):
s = ''.join(s)
return [s[i:i+step] for i in range(0, len(s), step)]
print(func('abc', 'd', 'efgh', step=2))
実行結果
['ab', 'cd', 'ef', 'gh']
まとめ
この記事では、Pythonの様々な引数について解説しました。
引数を位置専用やキーワード専用にすることで無駄な呼び出し方法を強制して関数の使い方を明確化することができます。
関数の使い方は以下の記事を参照してください。
それでは今回の内容はここまでです!ではまたどこかで〜( ・∀・)ノ