Java继承;将子类传递给超类的抽象方法

时间:2014-05-28 16:29:18

标签: java inheritance interface abstract

对不起标题,无法想出更明确的内容。 我有以下结构:

public interface Vehicle {...}
public class Car implements Vehicle {...}

然后:

public abstract class Fixer {
...
   abstract void fix(Vehicle vehicle);
...
}

并希望:

public class CarFixer extends Fixer {
    void fix(Car car) {...}
}

但这不起作用。 Eclipse说:The type CarFixer must implement the inherited abstract method Fixer.fix(Vehicle)。知道怎么解决这个问题?

2 个答案:

答案 0 :(得分:8)

您可以使用泛型来解决此问题:

public abstract class Fixer<T extends Vehicle> {
    abstract void fix(T vehicle);
}

public class CarFixer extends Fixer<Car> {
    void fix(Car car) {...}
}

原始版本的问题在于fix方法允许任何类型的车辆,但您的实施类只允许使用汽车。请考虑以下代码:

Fixer fixer = new CarFixer();
fixer.fix(new Bike()); // <-- boom, `ClassCastException`, Bike is a vehicle but not a car

答案 1 :(得分:3)

你遇到了generics的卑微之家。

泛型提供了一种'通配符'类型,其中类或方法可以指定'我们真的不关心它是什么类型,我们只需要-a type'< / em>的

泛型允许 super 类在类中强制执行特定类型,而不是允许扩展某个类的任何类类。

这意味着您最终会强制执行新的允许的最高超类作为参数(即Vehicle不再是您可以传递给{{1}的最基本允许类型它现在是子类所说的,只要该任意类型扩展fix())。

泛型的常见位置是container classes(即VehicleListMap),其中容器并不真正关心它跟踪的类型,而是专注于实际跟踪和管理这些实例。

泛型由一个或多个类型的占位符组成(在Java中,SetE是常用的,但名称并不重要;它们通常遵循使用的常规类型命名约定)代替特定的班级或超级班级。


在您的代码中,您希望子类在给定其确切相关类型的情况下实现方法(即T需要CarFixer s,Car需要JetpackFixer s)但是你想强制这些类型扩展Jetpack

为了强制执行此操作,您必须准确告诉Vehicle类您的子类想要什么。

Fixer

然后你的子类扩展了Fixer,用它想要的类型填充public abstract class Fixer <E extends Vehicle> { abstract void fix(E vehicle); }

E