(int a, int b)、(a, b)、a(單參數可省括號)->{ return ...; }Lambda 本身**無獨立類型**,類型由**上下文目標類型**決定:
// 同一 Lambda,不同目標類型
Runnable r = () -> System.out.println("hi"); // 目標類型 Runnable
Callable<Void> c = () -> { System.out.println("hi"); return null; } // 目標類型 Callable
編譯器根據**目標類型的唯一抽象方法簽名**推導 Lambda 參數類型、返回類型、拋出異常。
void execute(Runnable r) { r.run(); }
<T> T execute(Callable<T> c) { return c.call(); }
String s = execute(() -> "done"); // 呼叫 Callable 版本,因有返回值
this、區域變數直接指向外層int x = 1;
Runnable r = () -> System.out.println(x); // OK
// x = 2; // 編譯錯誤:x 不再 effectively final
Lambda 可序列化 **iff** 目標類型實作 Serializable 且所有捕獲參數可序列化。但官方**強烈不建議**序列化 Lambda(內部類同樣),因跨版本/編譯器穩定性無保障。
@FunctionalInterface
interface IntMath { int op(int a, int b); }
IntMath add = (a, b) -> a + b;
IntMath sub = (a, b) -> a - b;
int r = calculate(40, 2, add); // 42
掌握 Lambda 語法細節,能精準控制類型推導、避免捕獲陷阱、編寫更健壯的函數式代碼。