First: are you sure this code compiles, because it will give you at least 7 compiler errors.
This will be the correct code:
Well, once fixed, the wizlab�s answer is correct, it�s all about polymorphism. Take a look in the main method, you are creating a SuperBase object with a reference variable a1 of type SuperBase, there would not be any problem with that, but also you are creating a Base object with the reference variable b1 of type SuperBase too (here is the first polymorphic thing), and finally you are creating a Derived object with a reference variable c1 of type Base (here is the second polymorphic thing).
Then you are calling the print method inside the a1 variable, here there would not be problem, then you are calling the print method inside the b1 variable, but here remember that b1 is of type SuperBase, so b1 just know its own print method, the one inside of SuperBase (if you want the print method of Base class you must down-cast b1) and you are passing it a Derived object, but remember that Derived is grandchild of SuperBase, so a Derived object IS-A SuperBase object too. Finally you are calling the print method inside the c1 variable, remember c1 is of type Base, so c1 just know its own print method which takes a Base object as parameter and the one inherited from SuperBase, and (again) you are passing a Derived object and remember that a Derived object is a child of Base, so a Derived object IS-A Base too. Then the JVM decides that it will use the print method which takes a Base object.
Do you get it?
I hope this help you to understand it.