在Scala中实现Java接口方法

时间:2010-09-01 01:44:03

标签: scala

我在Java接口上定义的getHandler方法的实现失败了,我不知道为什么。这是方法签名:

<H extends EventHandler> H getHandler( Type<H> type, int index );

我在Scala中的实现是:

def getHandler[H <: com.google.gwt.event.shared.EventHandler]
    (aType: Type[H], index: Int): H 
    = new com.google.gwt.event.shared.EventHandler() {}

...但编译器给了我这条消息:

type mismatch;  
    found: java.lang.Object with com.google.gwt.event.shared.EventHandler
    required: H

我在哪里错了?

3 个答案:

答案 0 :(得分:4)

我认为这是因为您的实施不支持接口的合同。 H可以是 EventHandler的任何子类型,由aType参数的类型决定。但是,无论作为EventHandler参数传递什么,您的实现始终返回相同的匿名子类型aType

我不知道正确的实现是什么,但我看不出如何在不以某种方式使用aType参数的情况下实现这一点。

答案 1 :(得分:3)

添加到Lachlan's answer我想指出,简单地将返回类型转换为预期类型可能会产生灾难性后果。

考虑以下实现,其中我使用了一个命名类而不是问题中的匿名内部类:

class MyHandlerA extends EventHandler
class MyHandlerB extends EventHandler

object BadImplementation extends I {
  def getHandler[H <: EventHandler](typ : Type[H], index: Int) = {
    (new MyHandlerA).asInstanceOf[H] // BAD: This asInstanceOf is a lie!
  }
}

以下行会导致ClassCastException没有警告。

val b: MyHandlerB = BadImplementation.getHandler(new Type[MyHandlerB] {} , 0)

因此除了强制转换之外,实现还必须确保返回的处理程序实际上可以赋值给H或返回null或抛出异常。

答案 2 :(得分:1)

我认为这可能会使其编译:

def getHandler[H <: com.google.gwt.event.shared.EventHandler]
    (aType: Type[H], index: Int): H = {
  val h = new com.google.gwt.event.shared.EventHandler() {}
  h.asInstanceOf[H]
}

期待H。正如Lachlan所说,aType可能在某处需要。