我正在研究一种方法,它只给出一条信息:扩展ClassTag的类型(如果需要强保证来解析类型的某些部分,则可以将其更改为TypeTag)。我们没有给出一个示例,以便我们可以使用scala.reflect.runtime.currentMirror
从可用的Scala库中获取InstanceMirror
。我们没有得到构造这样一个示例所必需的参数。我只能获得这种泛型类型的RuntimeClass
。Scala有一个伴随对象的概念。我想检查给定泛型类T
的同伴对象是否扩展了一个特定的trait A
,将该对象转换为该trait,并调用被该同伴对象覆盖的方法。执行我所描述的操作的当前代码如下:
def invokeOverridenMethodOfCompanionObject[T : ClassTag]() {
import scala.reflect.runtime.currentMirror
import scala.reflect.runtime.universe.NoSymbol
val runtimeClass = scala.reflect.classTag[T].runtimeClass
val companion = currentMirror.classSymbol(runtimeClass).companion
companion match {
case NoSymbol => // do nothing
case _ =>
// The problem is this line
currentMirror.reflectModule(companion.asModule).instance match {
case s: A => s.invokeOverridenMethod
case _ => // do nothing
}
}
}
这种方法几乎是完美的。问题是,如果对象不是顶级的,即如果在另一个对象或类中声明了此方法,则此方法不再起作用。然后Scala会抱怨并吐出这个错误:
object <objectName> is an inner module, use reflectModule on an InstanceMirror to obtain its ModuleMirror
问题是我无法获得拥有伴随对象的符号/类型的示例镜像。我也不能构造那个示例,因为我也没有参数来构造一个伪构造函数。我也不能保证空值构造函数的存在,所以使用它们的噱头也是禁止的。在这些限制条件下,有没有一种方法可以实现我的目标?
编辑:我知道Java Class
可以允许人们通过名称搜索方法,然后调用它。我知道这是可能的,但我的解决方案也需要稍后传递对象。因此,对我来说,直接获得对象的变量引用是一个 * 必须 * 的。您可以假设在上面的代码块结束后,我返回了构造的伴随对象。
1条答案
按热度按时间8hhllhi21#
当类和它的同伴都定义在一个对象中时,它实际上工作fine。
不起作用的地方(在该范围中注解行)是如果它们是在 class 中定义的。为此,我认为没有示例你做不了什么,因为属于不同示例的对象是 * 不同的 *(也有不同的 * 类型 *):
(new Baz.Bat == new Baz.Bat) === false