如何扩展包含Scala的通用方法的Java接口?(How do I extend Java inte

2019-08-16 18:32发布

假设我们有以下的Java接口:

// Java
public interface Foo {
    <T> T bar(Class<T> c);
}

我应该如何在斯卡拉其扩展? 写作

// Scala
class FooString extends Foo {
  override def bar(c: Class[String]): String = "hello, world";
}

将使编译抛出“类FooString需要是抽象的,因为在类型的性状的Foo [T方法bar ] (类[T])没有被定义吨。”

提前致谢!

更新:丑陋的真相是:我在Java的泛型误解。

在任何情况下,我的困境的解决方案,显示在两个萨科和沃尔特的答案,但我更喜欢Walter的回答更好“因为它更简洁。

Answer 1:

这工作:

class FooString extends Foo {
  def bar[String](c: Class[String]): String = "hello world".asInstanceOf[String]
}

val fs = new FooString
println(fs.bar(classOf[String]))

编辑:

从@Eastsun的意见是正确的。 由于酒吧是类型参数T的通用方法,棒的Scala中实现必须是通用的方法为好。 我认为,在Scala中实现富的正确方法如下:

class FooString extends Foo {
  def bar[T](c: Class[T]): T = c.newInstance.asInstanceOf[T] // c gotta have a default constructor
}

val fs = new FooString
println(fs.bar(classOf[String]).getClass) // prints "class java.lang.String"
println(fs.bar(classOf[java.util.Date]).getClass) // prints "class java.util.Date"


Answer 2:

这是行不通的,因为你没有正确实现接口。 你的方法N阶的siganture必须是:

def bar[T](c:Class[T]):T

只有当你想实现吨符您可以修复行为的字符串。

第三次尝试,根据我们的讨论:

def bar[T](c:Class[T]):T = {
  // Some stuff
  val o:Any = myUntypedFunction(env)
  c.cast(o)
}

根据该上下文myUntypedFunction将创建一个对象,然后使用类参数来投你的结果,并获得一件T对象。 再次:这种行为是在Java和Scala中一样。



Answer 3:

你可以改变这样的:

public interface Foo<T> {
    T bar(Class<T> c);
}

class FooString extends Foo[String] {
    override def bar(c: Class[String]): String = "hello, world";
}


文章来源: How do I extend Java interface containing generic methods in Scala?