Python 高階関数 #1 map

株式会社リュディアです。今回は高階関数の 1 つである map についてまとめてみたいと思います。この記事では高階関数という用語は別にして map の使い方を見ていきます。

実は以前に JavaScript の高階関数についてもまとめています。興味のある方は以下のリンクを参照してください。

map はイテラブルなオブジェクトのそれぞれに何らかの関数で定義された処理を施してイテラブルなオブジェクトを返す関数です。具体例を見ていきましょう。

def double(x):
   return x*2

l_num = [0, 1, 2, 3, 4]

l_result = map(double, l_num)
print(l_result)       # 戻り値はイテレータであってリストでは無いことに注意
print(list(l_result)) # 表示するにはリスト型に変換する必要あり

# <map object at 0x000002B115CFA970>
# [0, 2, 4, 6, 8]

定義した関数 double は引数の値を2倍して返す関数です。またイテラブルなオブジェクトとしてリスト l_num を定義します。この l_num の各要素を2倍したリストが欲しい場合を考えます。ループを回せば対応可能なのですが、ここでは map 関数を使ってみます。map 関数の第1引数は処理が定義されている関数、ここでは double になります。処理を施したいイテラブルなオブジェクトは l_num です。結果を l_result で受けます。

ここで注意すべきは map の戻り値はイテレータオブジェクトであってリストでは無いことです。イテレータオブジェクトについて知識が怪しい人は以下のまとめ記事を見てください。

イテレータオブジェクトを表示しても内容はわからないので、list( ) でリスト型に変換すると元のリスト l_num の各要素が2倍されたリストになっていることがわかりますね。

ここまで処理して以前にまとめた内包表記と何が違うのか?と思われた方も多いかと思います。内包表記のまとめは以下を参考にしてください。

では、同じ処理を内包表記で行ってみます。

l_num = [0, 1, 2, 3, 4]

l_result = [i*2 for i in l_num]
print(l_result)

# [0, 2, 4, 6, 8]

同じ結果になりましたね。私個人は map 関数で処理できることは内包表記で対応可能だと考えているので最近は map 関数を使わなくなりました。

こうなると規模の大きなプログラムで map と内包表記でどちらが高速なのか?という議論にいきつきます。実行速度の比較は他のブログ等でも評価されていますのでそちらを参考になさってください。内包表記を使うべきという結論になっているものが多いと思います。

最後に関数定義を無名関数、いわゆる lambda(ラムダ)関数で実装した例を以下につけておきます。ラムダ関数については別途まとめる予定なので以下は参考です。

l_num = [0, 1, 2, 3, 4]

l_result = map(lambda x: x*2, l_num)
print(l_result)       # 戻り値はイテレータであってリストでは無いことに注意
print(list(l_result)) # 表示するにはリスト型に変換する必要あり

# <map object at 0x000002B115CFA970>
# [0, 2, 4, 6, 8]

高階関数に関するまとめの続きは以下からどうぞ。

では、ごきげんよう。


この記事が気に入ったらサポートをしてみませんか?