我有一些像这样的代码:
class ReflectiveJsonFormat[T:TypeTag] extends JsonFormat[T] {
def write(x: T) : JsValue = {
val t = typeOf[T]
val getters = t.declarations.filter { s => s.isMethod && s.asMethod.isGetter }
val mirror = runtimeMirror(this.getClass.getClassLoader)
val instanceMiror = mirror.reflect(x)
}
}
Run Code Online (Sandbox Code Playgroud)
最后一行失败了:
没有ClassTag可用于T
我以为TypeTag是比一个更多的信息ClassTag?我能得到ClassTag从TypeTag?如果没有,是否有一些语法可以说T有两个上下文边界 - 两个TypeTag和ClassTag?或者,您将如何修复此代码?
我坐在一个大约10000 LoC的项目前.我必须将此项目从Scala 2.9更新到2.10.这样做得很好,但由于清单,我收到了许多弃用警告.
在使用stackoverflow和许多其他站点的搜索功能之后,我没有那么多问题.我想总结一下; 关键点是:
TypeTags和ClassTag比Manifest和ClassManifest好得多.特别是你可以使用这些作为同义词(TypeTags < - > Manifests和ClassTags < - > ClassManifest)
TypeTag比ClassTag更强大,ClassTag更受限制TypeTags.我的第一个问题:在这个项目中,manifest[T].erasure.getSimpleName经常使用这种方法.现在我不仅可以将其切换为,typeTag[T].runtimeClass.getSimpleName因为代码不会编译,但是classTag[T].runtimeClass.getSimpleName它会编译.这会影响语义吗?(注意:该方法erasure也已弃用;您必须使用该方法runtimeClass)
第二个问题: Scala 2.9中的清单类型检查是:manifest[T] <:< manifest[A].在Scala 2.10中,我会写这个typeOf[T] <:< typeOf[A].但是<:<被弃用了?!
我可以将TypeTag转换为ClassTag吗?即:如果我只使用清单进行类型检查(Nr.3)和名称提取(Nr.2):我能将每个Manifest/ClassManifest重命名为ClassTag吗?