Java 10 New Feature: Local Variable Type Inference

In this tutorial, we’ll explore the Java 10 feature called Local Variable Type Inference, introduced through the Inference JDK Enhancement Proposal (JEP-286).

What is Local Variable Type Inference in Java 10?

Local Variable Type Inference, or type inference, refers to the automatic detection of a data type by the compiler based on the initialized value.

This feature introduces a more concise way to declare local variables in Java 10. While already present in languages like Scala, JavaScript, and C#, Java now adopts a similar approach.

Let’s compare it with how local variables were declared in previous Java versions.

In Java 5 and 6, an ArrayList holding strings would be declared as follows:

List<string> lists=new ArrayList<string>();

Here,

There are two parts here, Left-hand side and right-hand side of the equal operator

the left-hand side represents the variable declaration with its data type, and the right-hand side initializes the variable with a specified data type.

In this article, we are going to discuss how we can define local variable declaration with shorter and simple syntax.

In Java 7, Diamond operators introduced, Allows having empty brackets without type and variables were declared as below Before Java 7, ArrayList of string can be declared as follows

List<string> lists=new ArrayList<string>();

with Java 7, using Diamond operators, Reduced the code in such a way that the right-hand side is initialized without data type, and data type is inferred from the left-hand side.

List<String> lists=new ArrayList<>();

Java 10 further simplifies and reduces code by introducing the var keyword, maintaining type safety. The same ArrayList can now be declared as:

var lists=new ArrayList<String>();

The compiler infers the type from the right-hand side if no type is explicitly provided.

How Compiler Interprets var Types

When encountering a local variable with var, the compiler checks the right-hand side (initializer) to determine its type and assigns this type to the variable.

Let’s explore some examples of using var.

Basic Type Inference Example - var Keyword

In the below example, the local string is declared and initialized with string constant literal value.

Another local variable is declared and used to store the result of the lowercase of a string.

Type is not declared. The compiler automatically inferred the type from its value.

public class LocalVariableTypeInferenceHelloWorld {
    public static void main(String[] args) {
        var str = "THIS IS STRING";
        var lowerCaseString = str.toLowerCase();
        System.out.println(lowerCaseString);
        System.out.println(lowerCaseString.getClass().getTypeName());
    }
}

and output:

this is string
java.lang.String

Type safety with var example in java10

In the below example, created local String variable. assigned the same local variable with an integer.

This gives a compilation error

var str = "test string"; // equals to String str= "test string";
str=10;

The compiler still works with type safety Index.

For Loop local variable type inference example in java10

Declared index variables in for loop as like below.

 public class Test {
    public static void main(String[] args) {
        for (var i = 1; i <= 10; i++) {
            var temp= i* 2; // equals to Integer temp=i* 2;
            System.out.println(temp);
        }
    }
}

For each local variable type inference example

local variables can be inferred with var reserved word as like below.

Declared variable for iteration during for each iteration

import java.util.ArrayList;
public class ForEachVarDemo {
    public static void main(String[] args) {
        var list = new ArrayList<String>();
        list.add("abc");
        list.add("def");
        list.add("ggg");
        for (var str : list) {
            var upperString = str.toUpperCase(); // equal to String upperString = str.toUpperCase();
            System.out.println(upperString);
        }
    }
}

var variable inside the method and return value in java10

In a method, declared a local variable and returned it to the caller. And also returned value is stored in another local variable.

public class MethodLocalVarDemo {
 public static void main(String[] args) {
  var number1 = 30;
  var number2 = 50;
  var output = sum(number1, number2);
  System.out.println(output);
 }
 private static Integer sum(Integer number1, Integer number2) {
  var result = number1 + number2;
  return result;
 }
}

local variable for storing Ternary Operator result

local variables store the result of the ternary operator evaluation. In the below example, the result is inferred as String.

 var result = true? "true": "false";
System.out.println(result);

Declare a local variable for Streams

var assigns not only data types but also inferring streams.

Here is below example var stream example.

var list = new ArrayList<String>();
  list.add("abc");
  list.add("def");
  list.add("ggg");
  var stream = list.stream();
  stream.forEach((string) -> {
   System.out.println(string);
  });

local variable type Inference Compilation Errors

Local variables also have a lot of limitations and restrictions on the usage of this.

The below cases all give compilation errors.

  • No Local variable without an initializer
 var str;

Here local variable declares, but not initialized, it gives compilation errors like Cannot use 'var' on a variable without initializer.

  • No variable initialized with a null value
var str=null;

if var variable initialized with a null value, Compiler gives error - Cannot infer type for local variable initialized to ‘null’.

  • No Multiple or compound variables declaration

multiple local variables declarations are not allowed

var m=5,n=2,p=3;  // not allowed
int m=5,n=2,p=3;  //  allowed

if we declare multiple local variables, It gives var’ is not allowed in a compound declaration’.

  • No Local var array initializer

An array declared like below is not allowed for local variables.

var arrayDemo = { 61 , 14 };

the above line of code gives error Array initializer needs an explicit target-type

  • Not class instance variables

instance variables or class variables declared with local variables are not allowed.

public class ClassLocalDemo {
 var memberVariable=10;
 public static void main(String[] args) {
 }
}

  • No Method arguments/parameters

local variables do not declare in the method signature.

public class ClassLocalDemo {
 public static void main(String[] args) {
 }
 public static void method(var parame) {
 }
}

  • No var in Method return type

method return type should not be var word and throws a compilation error

public static var method() {
 }

  • No var declaration in a catch block

var is not allowed catch block as like below

public class Test {
    public static void main(String[] args) {
        try {
            // code
        } catch (var e) {
        }
    }

}
  • Lambda expression needs an explicit target-type

the below lambda expression var initialization throws an error.

Like the diamond operator, on the right-hand side, Need target data type to work

var helloString = () -> "teststring";

-Constructor arguments not allowed

var should do not use with constructor arguments as like below

public class Demo {
 public Demo(var a) {

 }
}

Java 10 Local Variables Inference Advantages and Disadvantages

Advantages:

  • Reduces boilerplate code
  • Enhances readability and requires less typing

Disadvantages Local variables declaration and the diamond operator in Java 7 can collide, leading to confusion among developers.

var is not a keyword; it is a reserved word, and names of variables and methods cannot use the word ‘var’ as they are not considered valid.

Conclusion

This tutorial covered the Local Variables Inference types in different Java versions with examples, highlighting the advantages and disadvantages of the var keyword.