通过反射获取Java Class
实例,能否获得 ClassTag
信息?
这是情况。我有一个 Scala 的 case class
如下:
case class Relation[M : ClassTag](id: UUID,
model: Option[M] = None)
这是使用方式(尽管有许多相关类):
case class Organization(name: String)
case class Person(firstName: String,
lastName: String,
organization: Relation[Organization])
我将尝试使用编程方式构建这些关系的树形结构,代码示例如下:
private def generateFieldMap(clazz: Class[_]): Map[String, Class[_]] = {
clazz.getDeclaredFields.foldLeft(Map.empty[String, Class[_]])((map, field) => {
map + (field.getName -> field.getType)
})
}
private def getRelationModelClass[M : ClassTag](relationClass: Class[_ <: Relation[M]]): Class[_] = {
classTag[M].runtimeClass
}
def treeOf[M: ClassTag](relations: List[String]): Map[String, Any] = {
val normalizedRelations = ModelHelper.normalize(relations)
val initialFieldMap = Map("" -> generateFieldMap(classTag[M].runtimeClass))
val relationFieldMap = relations.foldLeft(initialFieldMap)((map, relation) => {
val parts = relation.split('.')
val parentRelation = parts.dropRight(1).mkString(".")
val relationClass = map(parentRelation)(parts.last)
val relationModelClass = relationClass match {
case clazz: Class[_ <: Relation[_]] => getRelationModelClass(clazz)
case _ => throw ProcessStreetException("cannot follow non-relation: " + relation)
}
val fieldMap = generateFieldMap(relationModelClass)
map + (relation -> fieldMap)
})
relationFieldMap
}
val relations = List("organization")
val tree = treeOf[Person](relations)
这段代码无法编译。我遇到了以下错误:
[error] Foo.scala:148: not found: type _$12
[error] case clazz: Class[_ <: Relation[_]] => getRelationModelClass(clazz)
[error] ^
[error] one error found
[error] (compile:compile) Compilation failed
基本上,我想做的是在只有Java Class
时访问ClassTag
信息。这可行吗?
Relation[M]
中得到类型。例如,如果我执行ClassTag(clazz).runtimeClass
,我会得到Relation
类,但不是我想要的M
类。 - cdmckayM
调用classTag[M]
的情况。在这种情况下,我猜你运气不好。除非您使用具体类型参数调用该方法,否则您将无法仅通过Relation
的Java类检索Relation[M]
中的M
。这是可怕的类型擦除。 - Vladimir MatveevTypeTag
和Scala反射工具代替类和类标签。但是你需要将其用于所有内容。然后你就应该能够恢复泛型类型参数了。 - Vladimir Matveev