Java:通用接口,在运行时选择的实例

时间:2013-08-13 14:54:10

标签: java generics wildcard bounded-wildcard

我有以下简单的界面:

public interface ISimmilarityMeasure<T extends ResourceDescriptor> {
    public double getSim(T s, T t);
}

和类似

的实现
public class NormalizedLevenstheinSim implements
             ISimmilarityMeasure<SimpleResourceDescriptor> { ... }

public class JaccardCommentsSim implements
             ISimmilarityMeasure<LabelsCommentsResourceDescriptor> { ... }

SimpleResourceDescriptorLabelsCommentsResourceDescriptor都延伸

public abstract class ComparableResourceDescriptor
             implements ResourceDescriptor 

在运行时,我调用方法

public static ISimmilarityMeasure<? extends ResourceDescriptor> getSimInstance(){ }

将返回依赖于ResourceDescriptor的特定实例的ISimmilarityMeasure的实例“sim”。

我还创建了一个数组ResourceDescriptor[] candidates,它将在运行时保存特定ISimmilarityMeasure对象所需的ResourceDescriptor类型的实例。

但是,如果我尝试调用sim.getSim(candidates[0], candidates[1]),编译器会告诉我

"capture#3-of ? extends ResourceDescriptor ... is not applicable for the arguments (ResourceDescriptor ... "

我使用eclipse,如果我查看sim的可用方法,它会显示getSim(null s, null t)。 我不明白为什么会这样。如果编译器不清楚,getSim必须期望任何ResourceDescriptor,并且candidates中的每个对象都是ResourceDescriptor,因此允许调用吗?如果特定的ISimmilarityMeasure期望某种类型的ResourceDescriptor但是被传递给另一种类型的资源,那么它是否应该在运行时不是异常?

1 个答案:

答案 0 :(得分:2)

对于某种类型getSimInstance()

ISimmilarityMeasure<X>将返回X类型的对象。我们对X所了解的全部内容是它继承自ResourceDescriptor。在此对象上,您调用getSim(ResourceDescriptor, ResourceDescriptor)。但是,它不期望ResourceDescriptor参数,它期望X参数。

虽然X始终是ResourceDescriptor,但无法保证ResourceDescriptorX,因此您的编译器拒绝接受它。