final
in Java can refer to variables, methods and classes. There are three simple rules:
Usages
Good Programming Practice
Some developer consider it good practice to mark a variable final when you can. If you have a variable that should not be changed, you should mark it final.
An important use of final
keyword if for method parameters. If you want to emphasize that a method doesn't change its input parameters, mark the properties as final.
public int sumup(final List<Integer> ints);
This emphasizes that the sumup
method is not going to change the ints
.
Inner class Access
If your anonymous inner class wants to access a variable, the variable should be marked final
public IPrintName printName(){
String name;
return new IPrintName(){
@Override
public void printName(){
System.out.println(name);
}
};
}
This class doesn't compile, as the variable name
, is not final.
Effectively final variables are an exception. These are local variables that are written to only once and could therefore be made final. Effectively final variables can be accessed from anonymus classes too.
final static
variable
Even though the code below is completely legal when final
variable foo
is not static
, in case of static
it will not compile:
class TestFinal {
private final static List foo;
public Test() {
foo = new ArrayList();
}
}
The reason is, let's repeat again, final variable cannot be reassigned. Since foo
is static, it is shared among all instances of class TestFinal
. When a new instance of a class TestFinal
is created, its constructor is invoked and therefore foo gets reassigned which compiler does not allow. A correct way to initialize variable foo
in this case is either:
class TestFinal {
private static final List foo = new ArrayList();
//..
}
or by using a static initializer:
class TestFinal {
private static final List foo;
static {
foo = new ArrayList();
}
//..
}
final
methods are useful when base class implements some important functionality that derived class is not supposed to change it. They are also faster than non-final methods, because there is no concept of virtual table involved.
All wrapper classes in Java are final, such as Integer
, Long
etc. Creators of these classes didn't want that anyone can e.g. extend Integer into his own class and change the basic behavior of Integer class. One of the requirements to make a class immutable is that subclasses may not override methods. The simplest way to do this is to declare the class as final
.