JAVA 14

This Post I will like to showcase features of Java 14. The release of JDK 14 resumes the six-month release cadence of OpenJDK and signifies that this is working very well. Although some releases have been a little light on new features (JDK 13, for example), JDK 14 includes multiple exciting new features for developers.

In addition to the usual API changes and low-level JVM enhancements, JDK 14 also includes two language preview features in the form of records and pattern matching for instanceof. All Java developers are familiar with NullPointerExceptions, and now, thankfully, they have been improved to simplify debugging.

Java has always protected developers from the kind of common errors that occur in languages like C and C++ through the use of explicit pointers that can be manipulated and point to the wrong place. Sometimes, this can be useful, and developers have resorted to using undocumented and unsupported APIs like sun.misc.Unsafe.In JDK 14, there is a new incubator module providing a foreignmemory access API.

JAVA 14 Features

RECORDS

Java is an object-oriented language; you create classes to hold data and use encapsulation to control how that data is accessed and modified. The use of objects makes manipulating complex datatypes simple and straightforward.

The downside (until now) is that creating a data type has been verbose, requiring a lot of code even for the most straightforward cases

 public class Point {
   private final double x;
   
   private final double y;
   
   public Point(double x, double y) {
     this.x = x;
     this.y = y;
   }
   public double getX() {
     return x;
   }
   public double getY() {
     return y;
   }
 }

That's 14 lines of code just to represent a two-value tuple.
JDK 14 introduces records as a preview feature. Preview features are a relatively new concept that allows Java platform developers to include a new language or virtual machine feature without making it part of the Java SE standard.

By doing this, developers can try out these features and provide feedback, allowing changes, if required, before the feature becomes set in the standard. To use a preview feature, you must specify the command-line flag, --enable-preview, for both compilation and runtime. For compilation, you must also specify the -source flag.

A record is a much simpler way of representing a data class. If we take our Point example, the code can be reduced to a single line:
public record Point(double x, double y) { }
This takes nothing away from the readability of the code; we're immediately aware that we now have something that contains two double values called x and y that we can access using the standard access or method names of getX() and getY().
Let's examine records in greater detail.

To start with, records are a new kind of type. Records are a restricted form of class in the same way as an enum. A record has a name and a state description, which defines the components of the record.

In the Point example above, the state description is the doubles,x and y. Records are designed for simplicity, so they are implicitly final and cannot extend any other class (technically, all records extend the java.lang.Record class, preventing them from being a sub-class of anything else).

There is no restriction on a record implementing one or more interfaces. Records may not define any additional instance variables,although they can include static variables. All component state in a record is final, so no accessor (setter) methods are provided. If you need any of that, you need to use a full-blown class.

Records do have flexibility, though.

Often, the constructor needs to provide additional behavior beyond assigning values. If this is the case, we can provide an alternative implementation of the constructor:
  
    record Range(int min, int max) {
 	 public Range {
   		if (min > max) {
   	       throw new IllegalArgumentException(“Max must be >= min”);
        }
      }
    }
  
Note that the compact constructor definition is abbreviated, as specifying the parameters is redundant. Any of the members that are automatically derived from the state description can also be declared, so, for example, you can provide an alternative toString() or hashCode() implementation (or even in the Point example, the getX() method).

An important thing to note here is that the compact constructor must be public and can only throw an unchecked exception; there is no way to have it throw a checked exception.

PATTERN MATCHING instanceof

In some situations, you do not know the exact type of an object.To handle this, Java has the instanceof operator that can be used to test against different types. The drawback to this is that, having determined the type of an object, you must use an explicit cast if you want to use it as that type:
 
   if (o instanceof String) {
 		String s = (String)o;
 		System.out.println(s.length);
	}
 
In JDK 14, the instanceof operator has been extended to allow a variable name to be specified in addition to the type (this is also a preview feature). That variable can then be used without the explicit cast:
 
   if (o instanceof String s)
 	System.out.println(s.length);
 
The scope of the variable is limited to where its use is logically correct, so:
 
   if (o instanceof String s)
 	  System.out.println(s.length);
   else
 	 // s is out of scope here
 
The scope can also apply within the conditional statement, so we can do something like this:
if (o instanceof String s && s.length() > 4) ...
This makes sense since the length() method will only be called if o is a String. The same does not work with a logical or operation:
if (o instanceof String s || s.length() > 4) ...
In this case, s.length() needs to be evaluated, regardless of the result of whether o is a String. Logically, this does not work, and so, it will result in a compilation error.
Using the logical, and not the operator, can produce some interesting scoping effects:
  
    if (!(o instanceof String s && s.length() > 3)
      return;
    System.out.println(s.length()); // s is in scope here
  
Java 14 Features


HELPFUL NullPointerException

Anyone who's written more than a few lines of Java code will have experienced a NullPointerException at some point. Failing to initialize an object reference (or mistakenly explicitly setting it to null) and then trying to use the reference will cause this exception to be thrown.

In simple cases, finding the cause of the problem is straightforward. If we try and run code like this:
 
   public class NullTest {
 	List <String> list;

    public NullTest() {
   	 list.add("foo");
   }
  }
 
The error generated is:
 
   Exception in thread "main" java.lang.NullPointerException
		at jdk14.NullTest.<init>(NullTest.java:16)
		at jdk14.Main.main(Main.java:15)
 
Since we're referencing list on line 16, it's evident that list is the culprit and we can quickly resolve the problem. However, if we use chained references in a line like this:
a.b.c.d = 12;
When we run this, we might see an error like this:

Exception in thread "main" java.lang.NullPointerException at Prog.main(Prog.java:5)
The problem is that we are unable to determine, from this alone,whether the exception is as a result of a being null, b being null, or c being null. We either need to use a debugger from our IDE or change the code to separate the references onto different lines; neitherof which is ideal. In JDK 14, if we run the same code, we will see something like this:

Exception in thread "main" java.lang.NullPointerException:
 Cannot read field "c" because "a.b" is null at Prog.main(Prog.java:5)
Immediately, we can see that a.b is the problem and set about correcting it. I'm sure that this will make many Java developers lives much easier. This feature is turned off by default and requires the command-line flag -XX:+ShowCodeDetailsInExceptionMessages to enable it.

As you see, Java 14 has packed in a lot of new features that cannot be covered in one blog.So i will continue to cover it in another blog

ADDITIONAL RESOURCES

Comments

Popular posts from this blog

Headlines are Zoom e2e encryption,Amazon's face recognition incorrectly matches,Android 11,Go 1.15 and What’s new is Angular 10 & Vue.Js 3.0

Java 14 Continues.. new APIs of JDK14 and JVM Changes