加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

反射 – Scala宏注释上的类型参数

发布时间:2020-12-16 10:04:21 所属栏目:安全 来源:网络整理
导读:我正在尝试在 scala中使用宏注释,其中我的宏注释将采用另一种类型的参数.然后它将使用scala反射来查看传入的类型,并根据需要添加一些方法.Eg. trait MyTrait { def x: Int def y: Float}@MyAnnotation class MyClass //-- somehow,this annotation should re
我正在尝试在 scala中使用宏注释,其中我的宏注释将采用另一种类型的参数.然后它将使用scala反射来查看传入的类型,并根据需要添加一些方法.Eg.

trait MyTrait {
  def x: Int
  def y: Float
}

@MyAnnotation class MyClass //<-- somehow,this annotation should reference MyTrait

class MyAnnotation(val target: Any) extends StaticAnnotation {
  def macroTransform(annottees: Any*) = macro MyAnnotationImpl.impl
}
object MyAnnotationImpl {
  def impl(c: Context)(annottees: c.Expr[Any]*): c.Expr[Any] = {
    // if I can get a handle on the type MyTrait in here
    // then I can call .members on it,etc.
    ...
  }
}

基本上,与Using Scala reflection in Scala macros相同,除了使用宏注释.但是,当我尝试使用TypeTag模拟我的宏注释时

class MyAnnotation[T](val target: Any) extends StaticAnnotation {
  def macroTransform[T](annottees: Any*) = macro MyAnnotationImpl.impl[T]
}
object MyAnnotationImpl {
  def impl[T: c.WeakTypeTag](c: Context)(annottees: c.Expr[Any]*): c.Expr[Any] = {
    ...
  }
}

我明白了

[error] /Users/imran/other_projs/learn_macros/macros/src/main/scala/com/imranrashid/oleander/macros/MacrosWithReflection.scala:7: macro annotation has wrong shape:
[error]   required: def macroTransform(annottees: Any*) = macro ...
[error]   found   : def macroTransform[T](annottees: Any*) = macro ...
[error] class MyAnnotation[T](val target: Any) extends StaticAnnotation {
[error]       ^

我也尝试将类型作为我的注释的参数,所以我会使用它像@MyAnnotation(MyTrait)类Foo ….我可以将名称提取为类似于字符串的类似

val targetTrait = c.prefix.tree match {
  case Apply(Select(New(Ident(_)),nme.CONSTRUCTOR),List(Ident(termName))) => termName
}

但是,我不知道我能做什么,而那个String可以取回完整的类型.我也试过像@MyAnnotation(typeOf [MyTrait])类Foo …这样的变种,然后在我的宏里面的typeOf上使用c.eval,但是它也没有编译.

解决方法

在宏天堂2.0.0-SNAPSHOT中,我们有一个非常棘手的方法来访问宏注释的类型参数(当我们有专门的API时,情况将会改善,但是现在很难为scala反射引入新的功能.jar在宏天堂,所以目前的API有点粗糙).

目前,有必要在注释类上指定type参数,而不是在macroTransform方法上声明任何类型参数.然后,在宏扩展中,访问c.macroApplication并提取与传递的类型参数对应的无类型树.然后,按照Can’t access Parent’s Members while dealing with Macro Annotations中的描述进行c.typeCheck.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读