I implemented this code:
class A {
//some code
}
class B extends A {
// some code
}
class C {
public static void main(String []args)
{
Because, all the compiler sees is that an A is cast into a B. Since some A's can actually be B's this may work for those A's. By writing the explicit cast, you ensure that this particular A is actually a valid B. However, this is not the case.
A justA = new A();
A anAThatIsAlsoAValidB = new B(); // implicit cast to supertype
B b1 = (A) anAThatIsAlsoAValidB ; // Cast an A into a B. At runtime, this will work fine! Compiler allows casting A into B.
B b2 = (A) justA; // Cast an A into a B. At runtime, this won't work. Compiler has/uses no more info than above.
Here's why the compiler does not really know about the type:
com.example.ThridPartyType obj = new com.example.ThridPartyType();
B b = (B) obj.getSomeA();
// getSomeA() returns A and that is all the compiler knows.
// Depeding on the implementation of "ThridPartyType::getSomeA()" the A returned may or may not actually also be a valid B.
// Hence, if the cast works or not will only be known at runtime. If it doesn't, the Exception is thrown.