今回は、flaskのsessionの仕組みを調べている時に出会った、functoolsモジュールのpartialメソッドについてまとめました。2つのシーケンス(リスト)の各値を総当たりで処理したい場合などに便利なメソッドだと思います。実行環境は以下になります。
- OS: MACOSX
- Python: 3.7.3
- 公式ドキュメント: functools — 高階関数と呼び出し可能オブジェクトの操作
- 参考サイト:
この記事が参考になりましたら、幸いです。
1. functoolsモジュールとpartialメソッド
functoolsモジュールは、主に高階関数に関するモジュールです。functoolsモジュールでは、reduce
メソッドが特に有名だと思います。高階関数については以前記事を執筆していますので、そちらを参考にして頂ければと思います。
このfunctoolsモジュールのpartial
メソッドは、ある関数とその一部の引数を部分適用した新たな関数オブジェクト(partialオブジェクト)を生成します。この説明だとなにやら難しく聞こえますが、簡単に言えばある関数が2つ引数を取る場合、片方の引数は固定して、もう1つの引数をいじれるようにするということです。一部の引数を固定することで2つの配列の各値をfor文を使って総当たりで検証、処理する場合などに使い勝手が良いと思います。次の章で具体的なコード例を紹介していきます。
2. コード例
ここからはコード例とともに解説します。
2-1. コード例①
まずは、1つ目のコード例です。基本的な挙動がわかるよう、簡単なコードを作ってみました。
# 基本
from functools import partial
# 基本関数
def times(a, b):
return a * b
# 実行関数
def main(args):
# partialオブジェクトの生成
tentimes = partial(times, b=10)
print(type(tentimes))
return tentimes(args)
main(3)
# 戻り値
<class 'functools.partial'>
[12]: 30
このコード例では、基本となる関数はtimes
関数になり、このtimes
関数はa
とb
の2つの関数を取ります。これをmain
関数内でpartial
関数がラップしています。partial
関数は第1引数は対象とする関数オブジェクト、第2引数でその関数オブジェクトの引数を指定します。この時、キーワードを指定した場合はは基本関数のキーワード引数にその値が挿入され、単なる引数が指定された場合は基本関数の第1引数に挿入されます。上記の例では、partial
関数の引数でb=10
と指定しているので、times
関数の第2引数b
が10に固定されます。もしpartial(times, 10)
と記述した場合は,times
関数の引数a
が10に固定されるということになります。なお、変数tentimes
はpartial
オブジェクトですが、いわば関数オブジェクトのようなものだと言えるでしょう。main
関数の実行結果は上記のように30となります。
2-2. コード例②
2つ目のコード例です。
from functools import partial
def times(a, b):
return a * b
def main():
nums = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
tentimes = partial(times, 10)
return list(map(tentimes, nums))
main()
# 戻り値
[10, 20, 30, 40, 50, 60, 70, 80, 90, 100]
2次元配列ではないですが、times
関数の片方の引数を固定することで、リストの各値への総当たり処理を行なっています。リストが2つある場合などはpartial
関数は非常に便利だと思います。
3. 最後に
以上ががfunctoolsモジュールのpartialメソッドです。知名度は低いメソッドですが、知っているだけでかなりコードを書くのが楽になるメソッドだと思います。このような便利なメソッドをどんどん活用していくことで、コードの可読性やクオリティは上がっていくのかなと思います。読んでいただき、ありがとうございました。