Java

Java 21 – Unnamed Patterns and Variables

person in gray shirt holding a small paper with texts

Let’s say you have declared a variable in your Java program.

But you are not going to use it for some reason.

May be you declared an exception variable in a catch block but not going to use the variable at all:

try{

     //code
}catch(Exception e){
        System.out.println("Something bad happened here");
}

Or in a for loop statement:

for(Person p: personList){
          ++count;   //not using the variable 'p' declared in the loop statement at all.
}

Or in Pattern Matching of Records (introduced in recent versions of Java):

if(obj instanceof Person(String name,int age)){
           System.out.println(name); // not using 'age' variable 
}

These scenarios are examples of “The side effect of a statement is more important than the result” as quoted in Open JDK docs.

In these cases Java starting from version 21 , allows you to replace those variables using the underscore character (“_”).

This way when some one goes through your code and sees the underscore character they know that it is an unused variable.

This improves the readability of the code and the maintainability.

Let’s first see how this helps in Pattern Matching for Records.

Unused Patterns in Records:

Let’s say we have two records , a Person record and an Animal record:

record Person(String name, int age, Address address) {

}

record Address(String city, String country) {

}

record Animal(String type, String name) {
}

The Person record has one more child record named Address.

Now let’s say you have a method which prints the name of a record whether it is a Person or Animal.

Prior to Pattern Matching features introduced in latest versions of Java , you need a method similar to below to achieve this:


public void printName(Object o){
 

   if(o instanceof Person p){

            System.out.println(p.name());
    }else if(o instanceof Animal a){

             System.out.println(a.name());
      }

}

Using pattern matching of records you don’t have to initialize the record in the instanceof operator.

The above code could be replaced like below:

public void printName(Object o){
 

   if(o instanceof Person(String name,int age,Address address)){

            System.out.println(name);
    }else if(o instanceof Animal(String type,String name)){

             System.out.println(name);
      }

}

Without declaring a variable for either Person or Animal records we are able to print their names.

But still the code looks verbose.

We want only the name.

We don’t want the age and address for the Person and the type of animal for the Animal.

Java 21 simplifies this using unnamed variables.

You can replace the unused variables above using underscore.

So the above code becomes:

    public void printName(Object o) {

        if (o instanceof Person(String name, int  _, Address  _)) {

            System.out.println(name);
        } else if (o instanceof Animal(String  _, String name)) {

            System.out.println(name);
        }

    }

The code now clearly conveys that we are using only name variable .

Even one step further , you can replace a pattern (Variable type + Variable name) using underscore.

So you can replace int _ , Address _ and String _ in the above code with just _.

So the above code now becomes:

    public void printName(Object o) {

        if (o instanceof Person(String name, _,_)) {

            System.out.println(name);
        } else if (o instanceof Animal(_, String name)) {

            System.out.println(name);
        }

    }

Much simpler and readable now!

Unused Variables:

Now let’s see how to use this feature for variables used in other scenarios .

The for loop introduced in this article earlier now becomes:

for(Person _: personList){
          ++count;   //not using the variable 'p' declared in the loop statement at all.
}

Also the try catch block introduced earlier becomes:

try{

     //code
}catch(Exception _){
        System.out.println("Something bad happened here");
}

More readable and maintainable!

Note: This is a preview feature , so to run the above code you should set –enable-preview flag.

Example:

java --source 21 --enable-preview App.java

That’s it!

Reference:

https://openjdk.org/jeps/443


Posted

in

by

Comments

Leave a Reply

Discover more from The Full Stack Developer

Subscribe now to keep reading and get access to the full archive.

Continue reading