The Java final keyword: does it improve performance?

A common misconception I have come across is the idea that use of the Java final keyword is primarily a performance issue. The idea may have originated from other languaes where the final keyword may invoke a performance difference, and will usually be sold to you along the lines of: "If you make your class/method final, then the compiler can use extra optimisation". Chances are that the person in question isn't clear about the exact details of the optimisation in question or whether "the compiler" means the bytecode compiler or the JIT compiler. They probably haven't actually seen either any raw bytecode or any JIT-compiled assembler to back up their claim.

Now, I may be being slightly unfair in my criticism, because it's possible that some JVM somewhere implements an optimisation based on the final keyword1. But to the best of my knowledge, there are no class/method optimisations in Hotspot based on whether or not a class or method is final. In a discussion with members of the Hotspot compiler team back in 2005, they confirmed this was already the case then. And below, I present some performance data from a recent version of Hotspot indicating that this is still the case.

But if you think about it, we'd actually expect it to be the case. Even if you propose an optimisation based on whether or not a method/class has been overridden or extended, at any given moment in time, the JVM knows whether it has been overridden/extended or not. There's no need for the JVM to rely on the presence of any final marker added by the programmer to tell it whether or not to apply a particular optimisation!

There are optimisations implemented by Hotspot (and presumably other common JVMs) which rely on the JIT compiler being able to predict the exact subclass of a given object at a given point of execution. But those optimisation don't rely on the class/method being marked as final.

Well, that's the theory. On the next pages, we look at some actual data on the performance of final.

1. Some earlier bytecode compilers did erroneously choose to inline methods based on whether they were final. This optimisation turned out to be incorrect and is probably not present in any recent compilers.