When you make class Bat
final
, you're saying that this class can't be sub-classed. Since Bat
does not implement the interface Flyer
, the compiler is able to determine that b instanceof Flyer
can never be true
and raises an error.
This is specified in JLS section 15.20.2:
If a cast (§15.16) of the RelationalExpression to the ReferenceType would be rejected as a compile-time error, then the instanceof
relational expression likewise produces a compile-time error. In such a situation, the result of the instanceof
expression could never be true.
Additionally, from section 15.16 about cast expressions:
It is a compile-time error if the compile-time type of the operand may never be cast to the type specified by the cast operator according to the rules of casting conversion (§5.5).
In this case, Bat
can never be cast to Flyer
: it doesn't implement it and final
ensures that there can't be sub-classes that would implement it.
As you found out, the fixes are:
- Make
Bat
implement Flyer
: in this case, the instanceof
operator would always return true
.
- Remove the
final
identifier, implying that there could be sub-classes of Bat
implementing Flyer
.