第13回:エンジニアとしての矜持が許さない 〜ラムダはいつ使う?〜
■ それでも、まだやれるはずだ
最近、コードを書く機会が減った。
若手が書く。
最近はAIも書く。
設計はする。レビューもする。
だが、自分の手でラムダを書くことは、確実に減っている。
読めるようにはなった。
→ を見ても、もう止まらない。
だが、それで満足していいのか。
エンジニアとしての矜持が、それを許さない。
読めるだけでは足りない。
自分の手で書ける。
迷わず書ける。
若手と同じスピードで、自然に書ける。
俺はまだ、やれるはずだ。
■ なんでもラムダにできるわけではない
ここで一度、冷静になろう。
ラムダは魔法ではない。
「関数型インターフェース」の実装として使えるだけだ。
つまり、
- 抽象メソッドが1つだけ
- 処理をその場で渡したいとき
こういうときに使う。
■ 典型例
list.forEach(e -> System.out.println(e));
これは Consumer<T> という関数型インターフェースを
ラムダで実装している。
■ では、こういう場合は?
public void execute() {
int count = 0;
list.forEach(e -> {
count++; // コンパイルエラー
});
}
ローカル変数 count を変更しようとするとエラーになる。
なぜか?
ラムダ内では、ローカル変数は実質 final でなければならない。
つまり、
「外の状態を自由に変更する道具ではない」
ここが重要だ。
■ ここでラムダだ!と言える瞬間
ラムダが最もかっこいい瞬間は、
「処理を渡す」ときだ。
Collections.sort(list, (a, b) -> a.compareTo(b));
昔なら、こうだった。
Collections.sort(list, new Comparator<String>() {
@Override
public int compare(String a, String b) {
return a.compareTo(b);
}
});
長い。
本質は compare の1行だけなのに。
その「本質だけ」を書ける。
これがラムダの美しさだ。
■ 今日の練習問題(1問)
問題:
次の匿名クラスを、ラムダ式に書き換えよ。
Runnable r = new Runnable() {
@Override
public void run() {
System.out.println("Hello Lambda");
}
};
■ 解答
Runnable r = () -> System.out.println("Hello Lambda");
Runnable は抽象メソッドが1つ(run)だけ。
だからラムダにできる。
これが判断基準だ。
■ まとめ
- ラムダは「関数型インターフェース」の実装
- ローカル変数は実質 final
- 処理を渡すときに最も美しい
読めるようになった。
次は、書けるようになる。
エンジニアとしての矜持を、取り戻す。
■ 次回予告
ラムダは、ここで一区切り。
読めるようになった。 書けるようにもなった。
だが――
若手のコードには、まだ壁がある。
list.stream()
.filter(e -> e.startsWith("A"))
.map(String::toUpperCase)
.collect(Collectors.toList());
……長い。
何が返っているのか、一瞬止まる。
次は、ここだ。
Streamを、分解する。
0 件のコメント:
コメントを投稿