2 min read

Immutable Variables in Java

Java's final keyword and its usages on variables.
Immutable Variables in Java

The final Keyword

Immutable variables in Java use the final keyword. This keyword is placed before the type when defining a variable. Variables that are final follow the same camel case naming as regular variables. A final variable cannot be reassigned a value once a value is assigned. If a final variable is reassigned a value in code, this will result in a compiler error.

final var hello = "Hello";

// Compiler error:
//   cannot assign a value to final variable hello
hello = "Hi";

Local Variables

Final local variables are written with the following:

public static void main(final String[] args) {
    final var gretting = "Hello";
    
    // ...
}

Local variables marked as final do not have to be assigned a value when the variable is declared. Local final variables must be assigned before the value is used. If the variable is used before it is assigned a value, it will result in a compiler error.

public static void main(final String[] args) {
    final String s;
    
    if (args.length == 0) {
        s = "No args";
    }
    
    // Compiler error:
    //   variable s might not have been initalized
    System.out.println(s);
}

Local variables marked as final can guarantee that a variable has been assigned a value when you have multiple pathways through the code.

public static void main(final String[] args) {
    final String s;
    
    if (args.length == 0) {
        s = "0";
    } else if (args.length == 1) {
        s = "1";
    } else if (args.length > 1) {
        if (args.length == 2) {
            s = "2";
        } else {
            s = "Too many!";
        }
    } else {
        s = "?";
    }
    
    System.out.println(s);
}

Since the variable s is used at the end of the method, the compiler will guarantee there is a value assigned to it before it is used.

Start with your local variables as final. If you need to reassign a value to a final variable, try to find another way. If you absolutely can't, such as in the case of a loop counter, then remove the final keyword from the variable.

Method Variables

Final method variables cannot be reassigned a value and are written with the following:

public void concat(
        final String firstName,
        final String lastName) {

    // ...
}

Final method variables prevent a developer from being able to do the following:

public void reassign(int index) {
    index = 10;
    
    // prints 10
    System.out.println(index);
}

It is a good practice to always make method variables final. Reassigning method parameters is a bad practice.

Instance Variables

Instance variables that are final must be assigned a value either when they are declared or in the class constructor.

public class Name {

    private final String firstName;
    private final String lastName;

    public Name(
            final String firstName,
            final String lastName) {

        this.firstName = firstName;
        this.lastName = lastName;
    }
}

If you have overloaded constructors that call each other, a final variable must be assigned and can only be assigned once.

Conclusion

Immutable variables cannot be reassigned a value. They are declared with the final keyword before the variable type. Final variables must be assigned a value before they can be used.