Eğitim Portalı/Java/Java 9 Yenilikleri (2017)
Java01-java/55-java9-yenilikleri

Java 9 Yenilikleri (2017)

Java 9, dilin en büyük yapısal değişikliğini getirdi: Modül Sistemi (JPMS / Project Jigsaw). Bunun yanında günlük kodu kolaylaştıran birçok küçük ama değerli ekleme yaptı: koleksiyon fabrika metotları, Stream/Optional…

Java 9 Yenilikleri (2017)

Java 9, dilin en büyük yapısal değişikliğini getirdi: Modül Sistemi (JPMS / Project Jigsaw). Bunun yanında günlük kodu kolaylaştıran birçok küçük ama değerli ekleme yaptı: koleksiyon fabrika metotları, Stream/Optional eklentileri, private interface metotları ve jshell. Bu konuda, tek dosyada çalıştırılabilen pratik yenilikleri ele alıyoruz (modül sistemi yapısal olduğundan ayrıca açıklanır).

Koleksiyon fabrika metotları

Önceden değişmez bir koleksiyon kurmak çok adımlıydı; Java 9 bunu tek satıra indirdi:

List<String> l = List.of("a", "b", "c");
Set<Integer> s = Set.of(1, 2, 3);
Map<String,Integer> m = Map.of("bir", 1, "iki", 2);

Bu koleksiyonlar değişmezdir (eleman ekleme/silme UnsupportedOperationException atar) ve null kabul etmez. Sabit/yapılandırma verisi için idealdir.

Stream API eklentileri

  • takeWhile(p): Koşul bozulana kadar elemanları alır (sonra durur).
  • dropWhile(p): Koşul bozulana kadar elemanları atlar (sonra hepsini alır).
  • iterate(seed, hasNext, next): 3 argümanlı, sonlu üretim (for-döngüsü gibi).
  • Stream.ofNullable(x): x null ise boş, değilse tek elemanlı stream.

Optional eklentileri

  • ifPresentOrElse(action, emptyAction): Var/yok için iki dal.
  • or(supplier): Boşsa yedek bir Optional döndür.
  • stream(): Optional'ı 0/1 elemanlı stream'e çevir (Optional'ları düzleştirmek için flatMap(Optional::stream)).

Örnek 1 (./Ornek1.java) fabrikaları, Stream ve Optional eklentilerini gösterir.

Private interface metotları

Java 8 ile interface'lere default metotlar gelmişti; ama bu default metotların ortak kodunu paylaşmanın temiz bir yolu yoktu. Java 9, interface içinde private metotlara izin verdi:

interface Loglayici {
    default void bilgi(String m) { yaz("BİLGİ", m); }
    default void hata(String m)  { yaz("HATA", m); }
    private void yaz(String s, String m) { ... }   // ortak, dışarı sızmaz
}

try-with-resources iyileştirmesi

Java 9'dan itibaren try-with-resources, zaten var olan (effectively final) bir değişkeni doğrudan alabilir; yeni bir değişken tanımlaman gerekmez:

Baglanti b = ...;
try (b) { ... }   // Java 8'de: try (Baglanti b2 = b) gerekirdi

Örnek 2 (./Ornek2.java) private interface metotlarını ve bu iyileştirmeyi gösterir.

Modül Sistemi (JPMS) — kavramsal

Java 9'un en büyük yeniliği, paketlerin üstüne bir katman daha ekleyen modül sistemidir. Bir modül, module-info.java ile hangi paketleri dışa açtığını (exports) ve hangi modüllere ihtiyaç duyduğunu (requires) bildirir:

module com.egitim.uygulama {
    requires java.sql;
    exports com.egitim.uygulama.api;
}

Faydası: güçlü kapsülleme (iç paketler gizlenir), açık bağımlılıklar ve daha küçük çalışma zamanı (jlink ile özel JRE). Çoğu uygulama hâlâ classpath ile çalışır; modüller özellikle kütüphane ve platform geliştirmede önemlidir. (Modül sistemi tek dosyada gösterilemez; bu yüzden burada kavramsal anlatıldı.)

Ek: Java 9 ayrıca jshell (etkileşimli REPL), HTTP/2 istemcisinin ilk hali ve @Deprecated anotasyonuna forRemoval/since alanlarını getirdi.

Özet

Java 9'un pratik yeniliklerini öğrendik: koleksiyon fabrikaları (List/Set/Map.of), Stream (takeWhile/dropWhile/iterate/ofNullable) ve Optional (ifPresentOrElse/or/stream) eklentileri, private interface metotları ve try-with-resources iyileştirmesi (Örnek 1–2); en büyük yenilik olan modül sistemini kavramsal ele aldık. Sırada, tek bir anahtar kelimeyle gelen büyük kolaylık: Java 10 ve var.

Kod Örnekleri(2)

Ornek1

çalıştırılabilir
Ornek1.java
1// Ornek1: Java 9 — koleksiyon fabrika metotları, Stream ve Optional eklentileri.
2// Çalıştırma: java Ornek1.java
3import java.util.List;
4import java.util.Map;
5import java.util.Optional;
6import java.util.Set;
7import java.util.stream.Collectors;
8import java.util.stream.Stream;
9
10public class Ornek1 {
11
12    public static void main(String[] args) {
13        // 1) Koleksiyon fabrika metotları: tek satırda DEĞİŞMEZ koleksiyon.
14        List<String> liste = List.of("a", "b", "c");
15        Set<Integer> kume = Set.of(1, 2, 3);
16        Map<String, Integer> harita = Map.of("bir", 1, "iki", 2);
17        System.out.println("List.of: " + liste + " | Set.of: " + kume + " | Map.of: " + harita);
18
19        // 2) Stream eklentileri
20        // takeWhile: koşul bozulana kadar AL
21        System.out.println("takeWhile(<5): " + Stream.of(1, 2, 3, 7, 2).takeWhile(n -> n < 5).toList());
22        // dropWhile: koşul bozulana kadar ATLA
23        System.out.println("dropWhile(<5): " + Stream.of(1, 2, 3, 7, 2).dropWhile(n -> n < 5).toList());
24        // iterate (3 argümanlı): for-döngüsü gibi sonlu üretim
25        System.out.println("iterate      : " + Stream.iterate(1, n -> n <= 100, n -> n * 3).toList());
26        // ofNullable: null ise boş stream
27        System.out.println("ofNullable(null) eleman sayısı: " + Stream.ofNullable(null).count());
28
29        // 3) Optional eklentileri
30        Optional<String> dolu = Optional.of("değer");
31        Optional<String> bos = Optional.empty();
32        dolu.ifPresentOrElse(v -> System.out.println("var: " + v), () -> System.out.println("yok"));
33        bos.ifPresentOrElse(v -> System.out.println("var: " + v), () -> System.out.println("yok (else)"));
34        System.out.println("or(): " + bos.or(() -> Optional.of("yedek")).get());
35        // Optional.stream(): Optional'ları stream'de düzleştirmek için
36        long dolular = Stream.of(dolu, bos, Optional.of("x")).flatMap(Optional::stream).count();
37        System.out.println("dolu Optional sayısı: " + dolular);
38
39        System.out.println("""
40
41                --- Java 9: fabrikalar + Stream/Optional eklentileri ---
42                List/Set/Map.of: tek satırda değişmez koleksiyon (eski 3 adımlı kalıbın yerine).
43                Stream: takeWhile/dropWhile (koşullu al/atla), iterate (3 arg, sonlu), ofNullable.
44                Optional: ifPresentOrElse (var/yok dalı), or (yedek Optional), stream (düzleştirme).
45                Ayrıca Java 9'un en büyük yeniliği: Modül Sistemi (JPMS) ve jshell (tek dosyada gösterilemez).""");
46    }
47}
Çıktı yerel JDK 21 ile yakalandı — tarayıcıda JVM çalışmaz.

Ornek2

çalıştırılabilir
Ornek2.java
1// Ornek2: Java 9 — private interface metotları ve try-with-resources iyileştirmesi.
2// Çalıştırma: java Ornek2.java
3public class Ornek2 {
4
5    // Java 9: interface'lerde PRIVATE metot (default metotların ortak kodunu paylaşmak için).
6    interface Loglayici {
7        default void bilgi(String m) { yaz("BİLGİ", m); }
8        default void hata(String m) { yaz("HATA", m); }
9        // private: yalnızca interface içindeki default metotlar kullanır; dışarı sızmaz.
10        private void yaz(String seviye, String mesaj) {
11            System.out.println("[" + seviye + "] " + mesaj);
12        }
13    }
14
15    // Bir kaynak: try-with-resources ile otomatik kapanır.
16    static class Baglanti implements AutoCloseable {
17        final String ad;
18        Baglanti(String ad) { this.ad = ad; System.out.println("  " + ad + " açıldı"); }
19        @Override public void close() { System.out.println("  " + ad + " kapandı"); }
20    }
21
22    public static void main(String[] args) {
23        // private interface metodu: bilgi/hata ortak 'yaz' kodunu paylaşır.
24        Loglayici log = new Loglayici() {};
25        log.bilgi("uygulama başladı");
26        log.hata("bir şeyler ters gitti");
27
28        // Java 9: try-with-resources, ZATEN var olan (effectively final) değişkeni alabilir.
29        Baglanti b = new Baglanti("DB");
30        System.out.println("Java 9 try-with-resources (mevcut değişkenle):");
31        try (b) {                         // Java 8'de: try (Baglanti b2 = b) yazmak gerekirdi
32            System.out.println("  iş yapılıyor...");
33        }
34
35        System.out.println("""
36
37                --- Java 9: private interface metotları + try-with-resources ---
38                Private interface metotları: default metotların ORTAK kodunu interface içinde paylaşır,
39                dışarıya sızdırmadan (kod tekrarını önler).
40                try-with-resources: artık 'try (mevcutDegisken)' yazılabilir; yeni bir değişken
41                tanımlamak zorunda değilsin (kaynak effectively final olmalı).""");
42    }
43}
Çıktı yerel JDK 21 ile yakalandı — tarayıcıda JVM çalışmaz.