Pythonのラムダ式
今回はpythonです
# hatching from Java
class Lambda ():
def __init__ (self):
print()
# return only odd number by function
def test(data):
list = []
for v in data:
if v % 2 == 0:
list.append(v)
return list
# same function by different method
def test2(data):
return [v for v in data if v % 2 == 0]
# execute
if __name__ == '__main__':
# def data
data = list(range(10))+
# [0, 2, 4, 6, 8]
print('use function')
print(test(data))
# [0, 2, 4, 6, 8]
print('use function another')
print(test2(data))
# <filter object at 0x00000143D3A05608>
print('use filter & lambda')
print(filter(lambda v: v % 2 == 0, data))
# 0 2 4 6 8
for v in filter(lambda v: v % 2 == 0, data):
print(v)
やっぱラムダ式最高だわ
備忘録がてら解説書きます
普通のfor文
# return only odd number by function
def test(data):
list = []
for v in data:
if v % 2 == 0:
list.append(v)
return list
Javaの拡張for文と同じですね
for文の中でif文で、Listにaddしています
偶数のみを詰めて返却するメソッドになっています
javaだとこうですね ちょっと端折りますが
List<Integer> list = new LinkedList<>();
for (int i : Arrays.asList(0, 1, 2, 3)) {
if (i % 2 == 0) {
list.add(i);
}
}
どうにか1行で書いてみる
Javaの場合
もうこの時点でラムダに頼らざるを得ません
Arrays.asList(0, 1, 2, 3).stream()
.filter(v -> v % 2 == 0)
.forEach(System.out::println);
Pythonなら、for文1行で書けるし、付属的にif文を付け加えられる
def test2(data):
return [v for v in data if v % 2 == 0]
しかもこれって、streamのcollect(Collectors.toList())した後みたいに
配列で返してくれるんですよね
ラムダを使わずしてこの破壊力、さすがpython
filterとやら
Javaのstreamにしかみえませんねぇ
文法は
filter(ラムダで書いた条件, 繰り返す対象)
Javaのstreamでいうなら
filter(v -> v == 0)
みたいに条件に書く部分が第一引数で、そもそも配列などの捜査対象が第二引数ですね
filter(lambda v: v % 2 == 0, data)
dataが繰り返し対象のリストです
ラムダはJavaでいうFunction、引数と内部実装を書くものなので
勿論こういうこともできます
# 引数vが入ってきて、偶数のみを返す関数
stream = lambda v: v % 2 == 0
# 作ったstreamって関数の条件で、dataを絞る
filter(stream, data)
# このままだとコンソールに<filter object at 0x000002BC0F2D25C8>って出る
print(filter(stream, data))
# こうだとちゃんとリストの中身が出力されるよん
for v in filter(stream, data):
print(v)
最後の方でなんか変な感じになってますね
list.forEach(System.out::println)
みたいな、voidメソッドとしてのforを1行で書けないものですかね?
メソッドを何発もチェーンできるstreamAPIはそれはそれで優秀ですけど、調子に乗ると可読性も低くなりますし
素でこのくらい強いやつのがなんだかんだはかどりそうですね