Czym są wyrażenia lambda w Java i jakie możliwości one zapewniają?
sobes.tech AI
Odpowiedź od AI
Wyrażenia lambda w Javie to zwięzła składnia do tworzenia funkcji anonimowych (metod bez nazwy), które mogą być przekazywane jako argumenty lub przechowywane w zmiennych. W istocie są to funkcjonalne interfejsy implementowane "na żywo".
Główne możliwości, które zapewniają wyrażenia lambda:
-
Uproszczenie składni: Znacznie skracają kod boilerplate podczas pracy z interfejsami funkcyjnymi w porównaniu z anonimowymi klasami wewnętrznymi.
// Przed lambdą: Runnable classicRunnable = new Runnable() { @Override public void run() { System.out.println("Klasyczny Runnable"); } }; // Z lambdą: Runnable lambdaRunnable = () -> System.out.println("Lambda Runnable"); -
Programowanie funkcyjne: Pozwalają pisać bardziej funkcyjny kod, gdzie funkcje są obywatelami pierwszej klasy i mogą być przekazywane jako dane. To kluczowy element pracy z API Stream.
// Filtrowanie listy za pomocą lambda List<String> names = Arrays.asList("Alice", "Bob", "Charlie"); List<String> filteredNames = names.stream() .filter(name -> name.startsWith("A")) .collect(Collectors.toList()); -
Praca z API Stream: Wyrażenia lambda są podstawą dla większości operacji w API Stream (filter, map, forEach, reduce itp.), zapewniając zwięzłość i równoległe wykonanie.
// Transformacja i wyświetlenie elementów strumienia List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5); numbers.stream() .map(n -> n * n) // lambda do mapowania .forEach(System.out::println); // referencja do metody (alternatywa dla lambda) -
Ulepszenie czytelności: Dla prostych operacji lambdy czynią kod bardziej czytelnym i zrozumiałym, skupiając się na samej operacji, a nie na składni anonimowej klasy.
-
Implementacja interfejsów funkcyjnych: Mogą być używane wszędzie tam, gdzie oczekiwany jest egzemplarz interfejsu funkcyjnego (interfejs z jedną metodą abstrakcyjną).
Składnia wyrażenia lambda: (parametry) -> { ciało }
Przykłady:
- Bez parametrów, bez wartości zwracanej:
() -> System.out.println("Cześć") - Z jednym parametrem, bez wartości zwracanej:
name -> System.out.println("Cześć, " + name)(można pominąć nawiasy wokół pojedynczego parametru) - Z wieloma parametrami, bez wartości zwracanej:
(x, y) -> System.out.println(x + y) - Z parametrami, z wartością zwracaną:
(a, b) -> a + b(jeśli ciało składa się z jednej wyrażenia, jego wartość jest domyślnie zwracana) - Z parametrami, z blokiem kodu i wartością zwracaną:
(a, b) -> { int sum = a + b; return sum; }(wymagane jawnereturnw blokach kodu)