如何从Scala类型获取java.lang.reflect.Type?

Hen*_*son 2 scala

说我有一个方法:

def foo(t: java.lang.reflect.Type) = ???
Run Code Online (Sandbox Code Playgroud)

我想打电话给它(Int, Int).

这样的电话怎么样?我试过了:

foo(typeOf[(Int, Int)])
Run Code Online (Sandbox Code Playgroud)

但它似乎没有工作,因为它返回scala.reflect.runtime.universe.Type而不是java.lang.reflect.Type.

sen*_*nia 5

您应该使用classOf的方法Predef(它在默认情况下进口):

"".getClass
// Class[_ <: String] = class java.lang.String

classOf[String]
// Class[String] = class java.lang.String
Run Code Online (Sandbox Code Playgroud)

请注意foo,即使您要调用java接受的方法,也不应创建自己的方法java.lang.reflect.Type.你可以使用ClassTag:

import reflect.{ClassTag, classTag}

def javaFoo(t: java.lang.reflect.Type) = t.toString
def foo[T: ClassTag]() = javaFoo(classTag[T].runtimeClass)

foo[String]
// String = class java.lang.String
Run Code Online (Sandbox Code Playgroud)

正如您在呼叫方面所看到的,您不需要像classOf或那样的辅助功能typeOf.

键入擦除

作为@cmbaxter指出:由于类型擦除你不能得到TypeTuple2[Int, Int]- Type不包含有关类型参数的信息.您将获得TypeTuple2:

classOf[(Int, Int)] == classOf[(String, String)]
// Boolean = true

classOf[(Int, Int)] == classOf[(_, _)]
// Boolean = true
Run Code Online (Sandbox Code Playgroud)

  • 我在这里同意@senia.`Class`是`java.lang.reflect.Type`的一个实例,所以这将编译并运行.但请记住,如果你按原样使用它,并传入一个带泛型的类型(如你的例子,`Tuple2 [Int,Int]`,你将无法由于擦除而导出泛型类型. (2认同)