Po sześciu miesiącach prac rozwojowych firma Oracle wydała wersję Java SE 25 (Java Platform, Standard Edition 24), która wykorzystuje projekt open source OpenJDK jako implementację referencyjną. Z wyjątkiem usunięcia niektórych przestarzałych funkcji, Java SE 25 zachowuje wsteczną kompatybilność z poprzednimi wersjami platformy Java – większość wcześniej napisanych projektów Java będzie działać bez zmian w nowej wersji. Gotowe do instalacji kompilacje Java SE 25 (JDK, JRE i Server JRE) są przygotowane do… Linux (x86_64, AArch64), Windows (x86_64) i macOS (x86_64, AArch64). Opracowana przez projekt OpenJDK, implementacja referencyjna Java SE 25 jest w pełni open source na licencji GPLv2 z wyjątkiem GNU ClassPath, który umożliwia dynamiczne łączenie z produktami komercyjnymi.
Java SE 25 to wersja z rozszerzonym wsparciem technicznym, której aktualizacje będą dostępne do 2033 roku (zasadniczo do września 2030 roku). Java SE 17 i 21 będą również nadal wspierane w ramach gałęzi wsparcia długoterminowego (LTS), a aktualizacje będą dostępne odpowiednio do 2029 i 2031 roku (zasadniczo do 2026 i 2028 roku). Rozszerzone wsparcie techniczne dla gałęzi LTS Java SE 8 i 11 będzie kontynuowane do 2030 i 2032 roku.
Spośród 25 nowych funkcji zaproponowanych w Java SE (1, 2, 3, 4):
- Dodano eksperymentalne API StableValue do pracy z obiektami zawierającymi niezmienne dane i traktowanymi jako stałe w JVM. Do takich obiektów stosowane są optymalizacje wydajności podobne do tych dla pól ze słowem kluczowym „final”. API StableValue oddziela tworzenie wartości stałych od ich inicjalizacji, zapewnia, że wartość może zostać zainicjowana tylko raz, skraca czas uruchamiania programu i umożliwia zastosowanie optymalizacji składania stałych, które wcześniej były używane wyłącznie w kodzie wewnętrznym JDK, w kodzie użytkownika. class Application { // Wcześniej: // static final UserService USERS = new UserService(); // Teraz: static final StableValue UŻYTKOWNICY = StableValue.of(); public static UserService users() { return USERS.orElseSet(UserService::new); } }
- Dodano eksperymentalny interfejs API do kodowania i dekodowania obiektów z kluczami kryptograficznymi, certyfikatami i listami odwołanych certyfikatów przy użyciu formatu PEM (Pivacy-Enhanced Mail).
- Dodano obsługę wartości zakresowych, umożliwiając współdzielenie niezmiennych danych między wątkami i efektywną wymianę danych między wątkami potomnymi (wartości są dziedziczone). Wartości zakresowe zostały zaprojektowane w celu zastąpienia zmiennych lokalnych wątków i są bardziej wydajne w przypadku korzystania z bardzo dużej liczby wątków wirtualnych (tysiące lub miliony wątków). Główną różnicą między wartościami zakresowymi a zmiennymi lokalnymi wątków jest to, że są one zapisywane jednorazowo, nie można ich modyfikować i pozostają dostępne tylko przez czas wykonywania wątku.
- Dodano interfejs API umożliwiający korzystanie z funkcji wyprowadzania klucza kryptograficznego (KDF), które umożliwiają generowanie dodatkowych kluczy o wymaganej długości na podstawie klucza tajnego (np. hasła) i dowolnego zestawu danych.
- Usunięto kod i skrypty kompilacji obsługujące 32-bitowe systemy x86. Usunięcie obsługi 32-bitowych systemów x86 uprościło infrastrukturę kompilacji i testowania JDK oraz umożliwiło implementację funkcji specyficznych dla platformy bez konieczności tworzenia procedur obsługi awaryjnej dla 32-bitowych systemów x86.
- Dodano możliwość użycia pojedynczego polecenia „import module M” do zaimportowania wszystkich pakietów eksportowanych przez dany moduł. Ta zmiana znacznie upraszcza ponowne wykorzystanie bibliotek modułowych, umożliwiając dołączanie bibliotek i klas bez określania ich pozycji w hierarchii pakietów. Na przykład, polecenie „import module java.base” zaimportuje wszystkie 54 pakiety zawarte w module java.base, co wcześniej wymagałoby osobnych odwołań („import java.io.*”, „import java.util.*” itd.).
- Zaproponowano kompaktowe podejście do formatowania programów, które może być przydatne do nauki i tworzenia małych aplikacji. Kompaktowy format eliminuje potrzebę definiowania zbędnych klas, automatycznie importuje standardowe API i zapewnia uproszczone metody wejścia/wyjścia. Na przykład aplikację „Hello, World!” można zredukować do: void main() { IO.println("Hello, World!"); }
- Wyrażenia są dozwolone w konstruktorach przed wywołaniem super(…) używanym do jawnego wywołania konstruktora klasy nadrzędnej z konstruktora klasy pochodnej, pod warunkiem, że wyrażenia te nie odnoszą się do instancji tworzonej przez konstruktor. class Outer { void hello() { System.out.println("Hello"); } class Inner { Inner() { hello(); super(); } } }
- Dodano generatywny tryb zbieracza śmieci dla Shenandoah, który oddzielnie przetwarza stare i niedawno utworzone obiekty, aby zwiększyć wydajność zbierania obiektów o krótkim czasie życia. Ten nowy tryb zapewnia bardziej przewidywalną przepustowość, odporność na wahania obciążenia i mniejsze zużycie pamięci podczas zbierania śmieci. Harmonogram Shenandoah ma na celu skrócenie przestojów podczas zbierania śmieci poprzez wykonywanie większej ilości zadań równolegle z wykonywaniem aplikacji Java.
- Uproszczono ładowanie klas Ahead-of-Time i tworzenie pamięci podręcznej linkowania, co przyspiesza uruchamianie HotSpot JVM dzięki wykorzystaniu klas, które są już załadowane i powiązane. Oddzielne operacje rejestrowania aktywności i tworzenia pamięci podręcznej nie są już wymagane podczas uruchamiania; wystarczy jedno polecenie: java -XX:AOTCacheOutput=app.aot -cp app.jar com.example.App …
- Podczas uruchamiania maszyny wirtualnej HotSpot Java wprowadzono możliwość korzystania z profili wykonywania metod uzyskanych podczas poprzedniego uruchomienia aplikacji. Ta zmiana pozwala kompilatorowi JIT ominąć akumulację statystyk i natychmiast rozpocząć generowanie kodu natywnego bez oczekiwania na wygenerowanie profilu.
- HotSpot JVM implementuje obsługę kompaktowych nagłówków obiektów, których rozmiar w systemach 64-bitowych został zmniejszony z 96 do 64 bitów (z 12 do 8 bajtów). Zmniejszenie rozmiaru nagłówka redukuje rozmiar sterty i poprawia wydajność pamięci podręcznej.
- Zaproponowano testową implementację API Vector. Udostępnia ono funkcje do obliczeń wektorowych wykonywanych z wykorzystaniem instrukcji wektorowych procesorów x86_64 i AArch64 oraz umożliwia jednoczesne wykonywanie operacji na wielu wartościach (SIMD). W przeciwieństwie do automatycznej wektoryzacji operacji skalarnych w kompilatorze HotSpot JIT, nowe API umożliwia jawną kontrolę nad wektoryzacją w celu równoległego przetwarzania danych.
- Piąta wersja robocza interfejsu API współbieżności strukturalnej, który upraszcza tworzenie aplikacji wielowątkowych, traktując wiele zadań wykonywanych w różnych wątkach jako pojedynczą jednostkę, została udostępniona do testów.
- Moduł dopasowywania wzorców wprowadza trzecią wersję roboczą funkcji, która umożliwia używanie typów prymitywnych (int, byte, char i innych nieobiektowych typów bazowych) we wszystkich rodzajach szablonów, operatorze instanceof i blokach switch. switch (x.getStatus()) { case 0 -> "w porządku"; case 1 -> "ostrzeżenie"; case 2 -> "błąd"; case int i -> "nieznany status: " + i; } if (i instanceof byte b) { … b … }
- JDK Flight Recorder (JFR) dodaje eksperymentalną obsługę profilowania z dokładniejszym śledzeniem wykorzystania zasobów procesora na platformie. LinuxInformacje dotyczące czasu wykonania różnych struktur można czytelnie zwizualizować przy użyciu kolorowych diagramów FlameGraph.
- Poprawiono stabilność JDK Flight Recorder (JFR) podczas asynchronicznego próbkowania stosów wątków Java poprzez przechodzenie przez stos wywołań tylko w punktach bezpiecznych.
- JDK Flight Recorder (JFR) został zaktualizowany o nowe funkcje śledzenia i pomiaru czasu metod. Obsługuje śledzenie stosu wywołań określonych metod i rejestrowanie precyzyjnych statystyk wywołań metod, obejmujących takie wskaźniki, jak czas wykonania i liczba wywołań.
Źródło: opennet.ru
