Keep updated with the news from Java 11 to Java 17
Java has been updated a lot and brought many improvements to developers since Java 11. So let's see how you can improve your daily activities with Java 17.
But, before we start, I hope you already know the news from Java 8 to Java 11 and also know that Java 17 is an LTS version. If you don’t know what is it or needs to be updated with the previous versions, I recommend you to read this Java Improvements from 8 to 11.
Let’s go, let’s talk about Java 12, but before we start talking about it, let’s understand a little about what is JEP, and also what is a Preview feature.
JEP 1: JDK Enhancement Proposal
JEP is a document whose purpose is to add an enhancement to Java.
An enhancement is an effort to design and implement a nontrivial change to the JDK code base or to do some other kind of work whose goals, progress, and results are worth communicating broadly. A JDK Enhancement Proposal (hereinafter "JEP") should be drafted for any work that meets at least one of the following criteria:
It requires two or more weeks of engineering effort,
It makes a significant change to the JDK, or to the processes and infrastructure by which it is developed, or
It is in high demand by developers or customers.
NOTE: Not all improvements in the Java language are done by JEPs.
JEP 12: Preview Features
A preview feature is a new feature of the Java language, Java Virtual Machine, or Java SE API that is fully specified, fully implemented, and yet impermanent.
The preview feature is very useful for the Java language to keep improving, minimizing the break changes. The preview features are ready to be used, but it can change in the next versions, for that reason, it is not recommended to be used in production.
Java 12
This version introduces new things and some new features, following the JEP Preview approach. But let’s talk about only the things that are ready for production.
Compact Number Formatting
Java 12 comes with a new number formatter – the CompactNumberFormat. It's designed to represent a number in a shorter form, based on the patterns provided by a given locale.
Example:
public String compactNumberShort(Long value){
NumberFormat formatShort = NumberFormat.getCompactNumberInstance(new Locale("en", "US"), NumberFormat.Style.SHORT);
formatShort.setMaximumFractionDigits(2);
return formatShort.format(value);
}
New method teeing in the Collectors API
This method returns a Collector that is a composite of two downstream collectors. Every element passed to the resulting collector is processed by both downstream collectors, then their results are merged using the specified merge function into the final result.
public String minAndMaxValue(Integer... values) {
return Stream.of(values)
.collect(Collectors.teeing(
Collectors.maxBy(Integer::compareTo),
Collectors.minBy(Integer::compareTo),
(a, b) -> "Max - " + a.get() + " Min - " + b.get()
));
}
If you want to know more about what's new in Java 12:
Java 13
This version introduces new things, and we are going to talk about one of them that was introduced as a preview feature.
JEP 354 Switch Expressions (Second Preview)
Extend switch so it can be used as either a statement or an expression, and so that both forms can use either traditional case ... :
labels (with fall through)
new case ... -> labels (with no fall through)
In this version, Java introduces the Yield special word.
Most switch expressions will have a single expression to the right of the "case L ->" switch label. In the event that a full block is needed, was introduce a new yield statement to yield a value, which becomes the value of the enclosing switch expression.
Before:
int numLetters;
switch (day) {
case "MONDAY":
case "FRIDAY":
case "SUNDAY":
numLetters = 6;
break;
case "TUESDAY":
numLetters = 7;
break;
case "THURSDAY":
case "SATURDAY":
numLetters = 8;
break;
case "WEDNESDAY":
numLetters = 9;
break;
default:
System.out.println("Error: Not found day");
numLetters = day.length();
break;
}
return numLetters;
Now:
return switch (day) {
case "MONDAY","FRIDAY","SUNDAY" -> 6;
case "TUESDAY" -> 7;
case "THURSDAY", "SATURDAY" -> 8;
case "WEDNESDAY" -> 9;
default -> {
System.out.println("Error: Not found day");
yield day.length();
}
};
If you want to know more about Switch Expressions: https://openjdk.org/jeps/354
If you want to know more about what's new in Java 13:
Java 14
This version introduces many things, so let's get deep into that.
Switch Expressions (JEP 361)
Extend the switch so it can be used as either a statement or an expression. These were first introduced as a preview feature in JDK 12, and even in Java 13, but now, switch expressions have been standardized so that they are part and parcel of the development kit.
int numLetters = switch (day) {
case MONDAY, FRIDAY, SUNDAY -> 6;
case TUESDAY -> 7;
case THURSDAY, SATURDAY -> 8;
case WEDNESDAY -> 9;
};
Text Blocks (JEP 368 Second Preview)
Add text blocks to the Java language. A text block is a multi-line string literal that avoids the need for most escape sequences, automatically formats the string in a predictable way, and gives the developer control over the format when desired. These were first introduced as a preview feature in JDK 13 and kept as a preview in Java 14.
String html = """
<html>
<body>
<p>Hello, world</p>
</body>
</html>
""";
Records (JEP 359 Preview)
Records provide a compact syntax for declaring classes that are transparent holders for shallowly immutable data.
public record User(int id, String password) { };
Pattern Matching for instanceof (JEP 305 Preview)
JDK 14 has introduced pattern matching for instanceof with the aim of eliminating boilerplate code and making the developer's life a little bit easier.
Before:
public void doAction(Animal animal) {
if (animal instanceof Toucan) {
Toucan toucan = (Toucan) animal;
toucan.fly();
}
if (animal instanceof Lion) {
Lion lion = (Lion) animal;
lion.hunt();
lion.climbTree();
}
}
Now:
public void doAction(Animal animal) {
if (animal instanceof Toucan toucan) {
toucan.fly();
}
if (animal instanceof Lion lion) {
lion.hunt();
lion.climbTree();
}
}
Helpful NullPointerExceptions (JEP 358)
Improve the usability of NullPointerExceptions generated by the JVM by describing precisely which variable was null.
a.b.c.i = 99;
Exception in thread "main" java.lang.NullPointerException: Cannot read field "c" because "a.b" is null at Prog.main(Prog.java:5)
If you want to know more about what's new in Java 14:
Java 15
In this version, the Text Blocks become a fully supported product feature in Java 15 (JEP 378). And we have another amazing preview feature, called Sealed Classes.
Furthermore, in this version, we also have ZGC(JEP 377) and Shenandoah(JEP 379) available for production.
Sealed Classes (JEP 360 Preview)
Before Sealed Classes, Java didn't provide any fine-grained control over the inheritance. Sealed classes solve this problem. Sealed classes and interfaces restrict which other classes or interfaces may extend or implement them.
It's important to note that any class that extends a sealed class must itself be declared sealed, non-sealed, or final. This ensures the class hierarchy remains finite and known by the compiler.
public abstract sealed class Shape
permits Circle, Rectangle, Square {...}
public final class Circle extends Shape {...}
public sealed class Rectangle extends Shape
permits TransparentRectangle, FilledRectangle {...}
public final class TransparentRectangle extends Rectangle {...}
public final class FilledRectangle extends Rectangle {...}
public non-sealed class Square extends Shape {...}
Sealed classes work well with records (JEP 384), another preview feature of Java 15. Records are implicitly final, so a sealed hierarchy with records is slightly more concise than the example above:
public sealed interface Expr
permits ConstantExpr, PlusExpr, TimesExpr, NegExpr {...}
public record ConstantExpr(int i) implements Expr {...}
public record PlusExpr(Expr a, Expr b) implements Expr {...}
public record TimesExpr(Expr a, Expr b) implements Expr {...}
public record NegExpr(Expr e) implements Expr {...}
If you want to know more about what's new in Java 15:
Java 16
The Records is a fully supported product feature in Java 16 (JEP 395).
Pattern Matching for instanceof is a fully supported product feature in Java 16 (JEP 394).
In this version, the codebase was migrated to GitHub (https://github.com/openjdk/) by JEB 369
Stream.toList method (JDK-8180352)
The aim is to reduce the boilerplate with some commonly used Stream collectors, such as Collectors.toList and Collectors.toSet:
List<Integer> ints = integersAsString.stream().map(Integer::parseInt)
.collect(Collectors.toList());
List<Integer> intsEquivalent = integersAsString.stream().map(Integer::parseInt).toList();
Note: be careful, the .toList() and .toSet() return an immutable collection.
Stream.mapMulti method
The method mapMulti is used to apply a one-to-many transformation to the elements of the stream and flattens the result elements into a new stream. This method is preferable to flatMap in the following circumstances:
When replacing each stream element with a small (possibly zero) number of elements. Using this method avoids the overhead of creating a new Stream instance for every group of result elements, as required by flatMap.
When it is easier to use an imperative approach for generating result elements than it is to return them in the form of a Stream.
return Stream.of(values)
.<Triple>mapMulti((a, b) -> IntStream.range(1, a)
.mapToObj(n -> new Triple(n, a))
.forEach(b))
.collect(Collectors.toList());
Warnings for Value-Based Classes
Users of the value-based classes provided by the standard libraries—notably including users of the primitive wrapper classes—should avoid relying on the identity of class instances. Programmers are strongly discouraged from calling the wrapper class constructors, which are now deprecated for removal. New javac warnings discourage synchronization on value-based class instances. Runtime warnings about synchronization can also be activated, using the command-line option -XX:DiagnoseSyncOnValueBasedClasses.
For further details, see JEP 390.
The Valhalla Project is pursuing a significant enhancement to the Java programming model in the form of primitive classes. Such classes declare their instances to be identity-free and capable of inline or flattened representations, where instances can be copied freely between memory locations and encoded using solely the values of the instances' fields.
If you want to know more about what's new in Java 16:
Java 17 (LTS)
Java 17 was released on 14th September 2021, this is an LTS version and has extended support until September 2029.
In this version, Sealed Classes is a fully supported product feature in Java 17 (JEP 409).
Deprecate the Applet API for Removal (JEP 398)
Deprecate the Applet API for removal. It is essentially irrelevant since all web browser vendors have either removed support for Java browser plug-ins or announced plans to do so.
The Applet API was previously deprecated, though not for removal, by JEP 289 in Java 9.
Pattern Matching for Switch (JEP 406 Preview)
Extending pattern matching to switch allows an expression to be tested against several patterns, each with a specific action so that complex data-oriented queries can be expressed concisely and safely.
Object o = 123L;
return switch (o) {
case Integer i -> String.format("int %d", i);
case Long l -> String.format("long %d", l);
case Double d -> String.format("double %f", d);
case String s -> String.format("String %s", s);
default -> o.toString();
};
Strongly Encapsulate JDK Internals (JEP 403)
Strongly encapsulate all internal elements of the JDK, except for critical internal APIs such as sun.misc.Unsafe. It will no longer be possible to relax the strong encapsulation of internal elements via a single command-line option, as was possible in JDK 9 through JDK 16.
Over the years the developers of various libraries, frameworks, tools, and applications have used internal elements of the JDK in ways that compromise security and maintainability.
If you want to know more about what's new in Java 17:
Conclusion
Java has evolved significantly and there are now many useful tools and resources that can help developers in their daily work.
This article aims to provide a constructive overview of the latest Java developments that can help with developer productivity.
Be aware that there are many other things and improvements to the JVM and Garbage Collector that we haven't covered here. So keep studying and stay up to date with Java news 😄