The final Keyword
final means “this cannot change again,” but exactly what it locks down depends on where you put it — a variable, a method, or a class. All three uses share the same spirit (immutability, non-overridability, non-extensibility) but apply to completely different things.
Applied to | Effect |
|---|---|
Variable | Cannot be reassigned once given an initial value |
Method | Cannot be overridden by any subclass |
Class | Cannot be extended/subclassed at all |
final variable
A final local variable, field, or parameter can be assigned exactly once. After that, any attempt to reassign it is a compile-time error.
final variables
final double PI_APPROX = 3.14159; PI_APPROX = 3.0; // error: cannot assign a value to final variable 'PI_APPROX'
final method
A final method can be inherited by subclasses, but it cannot be overridden — a subclass is not allowed to provide its own version. This is useful when a method implements logic that must behave identically for every subclass, no exceptions.
This does not compile
class Account {
final double calculateInterest(double balance) {
return balance * 0.01;
}
}
class SavingsAccount extends Account {
@Override
double calculateInterest(double balance) { // error: cannot override
return balance * 0.05; // final method
}
}final class
A final class cannot be extended at all — no class is permitted to subclass it, under any circumstances. The single most famous example in the entire JDK is String itself, which is declared final.
This does not compile
class MyString extends String { // error: cannot inherit from final 'String'
}String being final is a deliberate design decision, and it's part of the reason Strings can be trusted as immutable everywhere in the JDK. If String could be subclassed, some other code could override its methods to behave unexpectedly — for example, a malicious subclass could make equals() lie, or make length() return something inconsistent with the actual character data — quietly breaking any code (including core parts of the JDK, like security checks and hash-based collections) that assumes a String behaves the way String is documented to behave.
finalvariable — assigned once, never reassigned.finalmethod — inherited, but never overridden by a subclass.finalclass — cannot be extended by any subclass at all.