final (keyword)
final has three distinct meanings in Java depending on what it modifies: a variable that cannot be reassigned, a method that cannot be overridden, or a class that cannot be subclassed.
final variable
final int MAX = 100;
// MAX = 200; // compile error
final List<String> list = new ArrayList<>();
list.add("hi"); // the reference is final, but the list contents are mutable
final on a reference variable means the reference cannot be reassigned — but the object it points to can still be mutated. For full immutability, the object itself must be immutable.
final method
public class Parent {
public final void fixed() { /* cannot be overridden */ }
}
// In a subclass, attempting to override fixed() is a compile error.
final class
public final class Money {
// cannot be extended
}
String, Integer, and all wrapper classes are final — their contracts cannot be changed by subclassing.
Effectively final
A local variable that is never reassigned is "effectively final" even without the keyword. Lambdas and anonymous classes can capture effectively final variables:
int multiplier = 10; // effectively final (not reassigned)
Function<Integer, Integer> f = n -> n * multiplier;
Best practice
Make all fields final by default — reach for mutability only when needed. It is one of the easiest ways to make code simpler to reason about.