Why is changing the return type of an abstract method in a child class allowed?
abstract class Animal {
public abstract Animal assing(Animal a);
}
class Lizard extends Animal {
@Override
public Lizard assing(Animal a) {
return new Lizard();
}
}
class Chicken extends Animal {
@Override
public Chicken assing(Animal a) {
return new Chicken();
}
}
whereas changing the parameter type is not allowed:
abstract class Animal {
public abstract void foo(int x);
}
class Lizard extends Animal {
// compiler error
// the type Lizard must implement the inherited abstract method Animal.foo(int)
public void foo(float x) {
}
}
class Chicken extends Animal {
@Override
public void foo(int x) {
}
}
Because, overriden methods
are allowed to have co-variant returns from java 1.5+ version .
Also to add when you change the parameter type in your concrete class you are basically declaring a completely new method which is different from your abstract method defined in your abstract class. Remember you need(forced by the compiler) to implement/override those abstarct methods in your concrete class which extends your abstract class.
Simply put here are the Rules for Overriden methods in java:
In your question you mix up two aspects: using a subtype in the overriding method and using a completely unrelated type , and a primitive at that, in the method arguments.
You can never, in no context, change an int
from a overridden method into a float
in the overriding method. The only special case that is allowed is return type covariance. Theoretically, the argument types could be contravariant, but that would make a mess out of method overload resolution, which is already very complex.
Overridden methods should have Same number of method parameters and their type should be same. But they are allowed to have covariant returns
To state this differently: A method that returns a subtype of the one required by the abstract method still fulfills the contract. While a method that takes a float does not fulfill the contract that the method takes an int.
Covariant return, means that when one overrides a method, the return type of the overridden method is allowed to be a subtype of the overridden method's return type. To clarify this with an example, a common case is Object.clone() - which is declared to return a type of Object. You could override this in your own class.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.