Java’da Fonksiyonel Programlama Nedir ve Lambda İfadeleri

Fonksiyonel programlama, veriyi bir dizi saf fonksiyonlar aracılığıyla işleme mantığına dayanır. Java 8 ile birlikte gelen lambda ifadeleri ve fonksiyonel arayüzler, fonksiyonel programlamayı Java’da mümkün kılar. Fonksiyonel programlama, özellikle koleksiyonlar üzerinde karmaşık veri işleme operasyonlarını daha sade ve anlaşılır bir şekilde ifade etmeyi sağlar.

Lambda İfadeleri

Lambda ifadeleri, Java’da anonim fonksiyonlar yazmanızı sağlar. Bu sayede fonksiyonel arayüzleri kısa ve öz bir şekilde kullanabilirsiniz. Örneğin:

List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);

numbers.stream()
       .map(n -> n * n)
       .forEach(System.out::println);

Yukarıdaki örnekte, her bir elemanı karesiyle eşleyip ekrana yazdırıyoruz. Lambda ifadeleri sayesinde bu tür işlemler birkaç satırda oldukça okunabilir bir şekilde gerçekleştirilebiliyor.

Fonksiyonel Arayüzler

Fonksiyonel arayüzler, yalnızca tek bir soyut metoda sahip olan arayüzlerdir. Java’da birçok hazır fonksiyonel arayüz vardır, örneğin:

Predicate: Belirli bir koşulu test eden fonksiyonel arayüzdür ve boolean döner.

Predicate<String> isLongerThanFive = str -> str.length() > 5;
System.out.println(isLongerThanFive.test("Merhaba")); // true

Function: Bir değer alıp başka bir değere dönüştüren fonksiyonel arayüzdür.

Function<Integer, String> intToString = num -> "Sayı: " + num;
System.out.println(intToString.apply(10)); // "Sayı: 10"

Consumer: Bir değer alır ve bir şey yapar fakat geri dönüş değeri yoktur.

Consumer<String> print = s -> System.out.println(s);
print.accept("Lambda ifadeleri güzeldir!");
Lambda İfadeleri ve Scope

Lambda ifadeleri, yerel değişkenleri kullanabilir ancak bu değişkenler final ya da effectively final (yani değişmeyen) olmalıdır. Örneğin:

String greeting = "Merhaba";
List<String> names = Arrays.asList("Ali", "Ayşe", "Mehmet");

names.forEach(name -> System.out.println(greeting + ", " + name));

Burada greeting değişkeni lambda içinde kullanılıyor ve effectively final olarak kabul ediliyor, çünkü değeri değiştirilmiyor.

Ekstra Kod Örnekleri

1) Liste Elemanlarını Filtreleme ve Lambda ile Kullanma

List<String> animals = Arrays.asList("Kedi", "Köpek", "Kaplan", "Tavşan");

animals.stream()
       .filter(animal -> animal.startsWith("K"))
       .forEach(System.out::println);

Bu örnekte, “K” harfiyle başlayan hayvanları filtreleyip ekrana yazdırıyoruz. Lambda ifadeleri sayesinde filtreleme işlemi oldukça basit hale geliyor.Bu örnekte, “K” harfiyle başlayan hayvanları filtreleyip ekrana yazdırıyoruz. Lambda ifadeleri sayesinde filtreleme işlemi oldukça basit hale geliyor.

2) Liste Elemanlarını Dönüştürme ve Yeni Listeye Toplama

List<Integer> nums = Arrays.asList(1, 2, 3, 4, 5);

List<Integer> squares = nums.stream()
                            .map(n -> n * n)
                            .collect(Collectors.toList());

System.out.println(squares); // [1, 4, 9, 16, 25]

Bu örnekte, verilen sayıların karelerini alıp yeni bir listeye topluyoruz. map() fonksiyonu her bir elemanı dönüştürmeye olanak sağlıyor.

3) Lambda ve Comparator Kullanımı

Lambda ifadeleri Comparator arayüzü ile birlikte oldukça güçlü bir şekilde kullanılabilir. Örneğin, bir listeyi özel bir sıralamaya göre sıralamak istiyorsanız:

List<String> cities = Arrays.asList("İstanbul", "Ankara", "İzmir", "Bursa");

cities.sort((c1, c2) -> c2.length() - c1.length());
System.out.println(cities); // ["İstanbul", "Ankara", "İzmir", "Bursa"]

Yukarıdaki örnekte, şehir isimlerini uzunluklarına göre ters sıraladık. Comparator arayüzünü lambda ifadesi ile kullanarak sıralama kriterini belirttik.


Bölüm 2’de Java’da fonksiyonel programlamanın ne olduğunu ve lambda ifadelerini ele aldık. Lambda ifadeleri ve fonksiyonel arayüzler sayesinde Java’da kodlar daha sade ve anlaşılır hale gelmektedir. Fonksiyonel programlama, özellikle büyük veri setleri üzerinde çalışırken kodun okunabilirliğini artırır ve hataların önlenmesine yardımcı olur.