Neue Java 13-Funktionen

1. Übersicht

Im September 2019 wurde JDK 13 gemäß Javas neuer Release-Trittfrequenz von sechs Monaten veröffentlicht . In diesem Artikel werden wir uns die neuen Funktionen und Verbesserungen ansehen, die in dieser Version eingeführt wurden.

2. Vorschau der Entwicklerfunktionen

Java 13 hat zwei neue Sprachfunktionen eingeführt, allerdings im Vorschaumodus . Dies bedeutet, dass diese Funktionen vollständig implementiert sind, damit Entwickler sie bewerten können, jedoch nicht produktionsbereit sind. Außerdem können sie aufgrund von Feedback entweder entfernt oder in zukünftigen Versionen dauerhaft gemacht werden.

Wir müssen –enable-Preview als Befehlszeilenflag angeben , um die Vorschaufunktionen verwenden zu können . Schauen wir sie uns genauer an.

2.1. Ausdrücke wechseln (JEP 354)

Wir haben anfangs Switch-Ausdrücke in JDK 12 gesehen. Die Switch- Ausdrücke von Java 13 bauen auf der vorherigen Version auf, indem eine neue Yield- Anweisung hinzugefügt wurde .

Mit Yield können wir jetzt effektiv Werte aus einem Schalterausdruck zurückgeben :

@Test @SuppressWarnings("preview") public void whenSwitchingOnOperationSquareMe_thenWillReturnSquare() { var me = 4; var operation = "squareMe"; var result = switch (operation) { case "doubleMe" -> { yield me * 2; } case "squareMe" -> { yield me * me; } default -> me; }; assertEquals(16, result); }

Wie wir sehen können, ist es jetzt einfach, das Strategiemuster mit dem neuen Schalter zu implementieren .

2.2. Textblöcke (JEP 355)

Die zweite Vorschaufunktion sind Textblöcke für mehrzeilige Zeichenfolgen wie eingebettetes JSON, XML, HTML usw.

Um JSON in unseren Code einzubetten, haben wir es früher als String- Literal deklariert :

String JSON_STRING = "{\r\n" + "\"name\" : \"Baeldung\",\r\n" + "\"website\" : \"//www.%s.com/\"\r\n" + "}";

Schreiben wir nun denselben JSON mit String- Textblöcken:

String TEXT_BLOCK_JSON = """ { "name" : "Baeldung", "website" : "//www.%s.com/" } """;

Es ist offensichtlich, dass es nicht erforderlich ist, doppelte Anführungszeichen zu umgehen oder einen Wagenrücklauf hinzuzufügen. Durch die Verwendung von Textblöcken ist der eingebettete JSON viel einfacher zu schreiben und leichter zu lesen und zu warten.

Darüber hinaus stehen alle String- Funktionen zur Verfügung:

@Test public void whenTextBlocks_thenStringOperationsWorkSame() { assertThat(TEXT_BLOCK_JSON.contains("Baeldung")).isTrue(); assertThat(TEXT_BLOCK_JSON.indexOf("www")).isGreaterThan(0); assertThat(TEXT_BLOCK_JSON.length()).isGreaterThan(0); } 

Außerdem verfügt java.lang.String jetzt über drei neue Methoden zum Bearbeiten von Textblöcken:

  • stripIndent () - ahmt den Compiler nach, um zufällige Leerzeichen zu entfernen
  • translateEscapes () - übersetzt Escape-Sequenzen wie "\\ t" in "\ t"
  • formatted () - funktioniert genauso wie String :: format, jedoch für Textblöcke

Werfen wir einen kurzen Blick auf ein String :: formatiertes Beispiel:

assertThat(TEXT_BLOCK_JSON.formatted("baeldung").contains("www.baeldung.com")).isTrue(); assertThat(String.format(JSON_STRING,"baeldung").contains("www.baeldung.com")).isTrue(); 

Da Textblöcke eine Vorschaufunktion sind und in einer zukünftigen Version entfernt werden können, werden diese neuen Methoden als veraltet markiert.

3. Dynamische CDS-Archive (JEP 350)

Class Data Sharing (CDS) ist seit einiger Zeit ein wichtiges Merkmal von Java HotSpot VM. Es ermöglicht die gemeinsame Nutzung von Klassenmetadaten zwischen verschiedenen JVMs, um die Startzeit und den Speicherbedarf zu verringern . JDK 10 erweiterte diese Funktion durch Hinzufügen von Anwendungs-CDS (AppCDS), um Entwicklern die Möglichkeit zu geben, Anwendungsklassen in das gemeinsam genutzte Archiv aufzunehmen. JDK 12 hat diese Funktion weiter erweitert und standardmäßig CDS-Archive hinzugefügt.

Das Archivieren von Anwendungsklassen war jedoch langwierig. Um Archivdateien zu generieren, mussten Entwickler zuerst Testläufe ihrer Anwendungen durchführen, um eine Klassenliste zu erstellen und diese dann in einem Archiv abzulegen. Danach kann dieses Archiv verwendet werden, um Metadaten zwischen JVMs auszutauschen.

Mit der dynamischen Archivierung hat JDK 13 diesen Prozess vereinfacht. Jetzt können wir zum Zeitpunkt des Beenden der Anwendung ein freigegebenes Archiv erstellen . Dadurch sind keine Probeläufe erforderlich.

Damit Anwendungen ein dynamisches freigegebenes Archiv über dem Standardsystemarchiv erstellen können, müssen Sie die Option -XX: ArchiveClassesAtExit hinzufügen und den Archivnamen als Argument angeben:

java -XX:ArchiveClassesAtExit= -cp  AppName

Wir können dann das neu erstellte Archiv verwenden, um dieselbe App mit der Option -XX: SharedArchiveFile auszuführen :

java -XX:SharedArchiveFile= -cp  AppName

4. ZGC: Nicht verwendeten Speicher freigeben (JEP 351)

Der Z Garbage Collector wurde in Java 11 als Garbage Collection-Mechanismus mit geringer Latenz eingeführt, sodass die GC-Pausenzeiten 10 ms nie überschritten. Im Gegensatz zu anderen HotSpot VM-GCs wie G1 und Shenandoah war es jedoch nicht dafür ausgestattet, nicht verwendeten Heapspeicher an das Betriebssystem zurückzugeben. Java 13 hat diese Funktion zum ZGC hinzugefügt.

Wir erhalten jetzt einen reduzierten Speicherbedarf und eine Leistungsverbesserung.

Ab Java 13 gibt der ZGC jetzt standardmäßig nicht festgeschriebenen Speicher an das Betriebssystem zurück , bis die angegebene Mindestgröße des Heapspeichers erreicht ist. Wenn wir diese Funktion nicht verwenden möchten, können wir auf folgende Weise zu Java 11 zurückkehren:

  • Verwenden der Option -XX: -ZUncommit oder
  • Festlegen der gleichen minimalen ( -Xms ) und maximalen ( -Xmx ) Heap-Größe

Zusätzlich hat ZGC jetzt eine maximal unterstützte Heap-Größe von 16 TB. Zuvor waren 4 TB die Grenze.

5. Implementieren Sie die Legacy Socket API (JEP 353) erneut.

Wir haben Socket- APIs ( java.net.Socket und java.net.ServerSocket ) seit ihrem Beginn als integralen Bestandteil von Java gesehen. Sie wurden jedoch in den letzten zwanzig Jahren nie modernisiert. In Java und C geschrieben, waren sie umständlich und schwer zu warten.

Java 13 bucked this trend and replaced the underlying implementation to align the API with the futuristic user-mode threads. Instead of PlainSocketImpl, the provider interface now points to NioSocketImpl. This newly coded implementation is based on the same internal infrastructure as java.nio.

Again, we do have a way to go back to using PlainSocketImpl. We can start the JVM with the system property -Djdk.net.usePlainSocketImpl set as true to use the older implementation. The default is NioSocketImpl.

6. Miscellaneous Changes

Apart from the JEPs listed above, Java 13 has given us a few more notable changes:

  • java.nio – method FileSystems.newFileSystem(Path, Map) added
  • java.time – new official Japanese era name added
  • javax.crypto – support for MS Cryptography Next Generation (CNG)
  • javax.security – property jdk.sasl.disabledMechanisms added to disable SASL mechanisms
  • javax.xml.crypto – new String constants introduced to represent Canonical XML 1.1 URIs
  • javax.xml.parsers – new methods added to instantiate DOM and SAX factories with namespaces support
  • Unicode support upgraded to version 12.1
  • Support added for Kerberos principal name canonicalization and cross-realm referrals

Zusätzlich werden einige APIs zum Entfernen vorgeschlagen. Dazu gehören die drei oben aufgeführten String- Methoden und die API javax.security.cert .

Zu den Entfernungen gehören das rmic- Tool und alte Funktionen aus dem JavaDoc-Tool. Pre-JDK 1.4 SocketImpl- Implementierungen werden ebenfalls nicht mehr unterstützt.

7. Fazit

In diesem Artikel haben wir alle fünf von Java 13 implementierten JDK-Erweiterungsvorschläge gesehen. Wir haben auch einige andere bemerkenswerte Ergänzungen und Löschungen aufgelistet.

Wie üblich ist der Quellcode über GitHub verfügbar.