scala 3宏:从宏返回Map[String,Class[Any]]

scala 3宏:从宏返回Map[String,Class[Any]],scala,macros,scala-macros,scala-3,Scala,Macros,Scala Macros,Scala 3,我正试图针对scala 3.0.0-M3编写一个宏。我希望宏返回某个类型的选项[u]字段的内部类型。例如,假设: class教授(val lastName:String,val id:Option[Int],val bossId:Option[Long]) 我想将id与Int相关联,将bossId与Long相关联 我有一些代码可以为基元类型执行此操作,并编译ok: 导入scala.quoted_ 导入scala.quoted.staging_ 导入scala.quoted.{Quotes,Ty

我正试图针对scala 3.0.0-M3编写一个宏。我希望宏返回某个类型的选项[u]字段的内部类型。例如,假设:

class教授(val lastName:String,val id:Option[Int],val bossId:Option[Long])
我想将id与Int相关联,将bossId与Long相关联

我有一些代码可以为基元类型执行此操作,并编译ok:

导入scala.quoted_
导入scala.quoted.staging_
导入scala.quoted.{Quotes,Type}
对象类型信息{
内联def字段信息[T(m.name->clazz))
}没有别的
}没有别的
}汤玛普先生
println(innerClassOfOptionFields)
Expr(innerClassOfOptionFields)
}
但如果我尝试使用它,就像这样:

class教授(val lastName:String,val id:Option[Int],val bossId:Option[Long])
对象主应用程序{
val fields=TypeInfo.fieldsInfo[教授]
}
编译器首先打印
Map(id->int,bossId->long)
,因为宏代码中的println看起来不错,但随后失败:

[error] 16 |  val fields = TypeInfo.fieldsInfo[Professor]
[error]    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
[error]    |               Found:    (classOf[Int] : Class[Int])
[error]    |               Required: Class[Any]
[error]    | This location contains code that was inlined from Main.scala:34

我做错了什么?我不应该从宏返回贴图,或者可能不是这样

请注意,我的宏中的if/else逻辑实际上并不重要,问题可以归结为(在其他条件相同的情况下):


您可以在给定的基础上定义此缺失

导入scala.quoted_
用{
def应用(x:Class[?])(使用引号)={
导入quotes.reflect_
Ref(defn.Predef_classOf).appliedToType(TypeRepr.typeConstructorOf(x)).asExpr.asInstanceOf[Expr[Class[?]]
}
}
在Scala 3的下一个版本中,这应该不再是必需的。标准库的给定实例也适用于
Class[?]

然后,您可以返回一个类型正确的
映射[String,Class[?]]

inline def fieldsInfo:Map[String,Class[?]=${fieldsInfoMacro}
def fieldsInfoMacro(使用引号):Expr[Map[String,Class[?]]={
val结果:映射[字符串,类[?]]=Map(
“bossId”->classOf[scala.Long],
“id”->classOf[scala.Int]
)
Expr(结果)
}
一切正常:

scala>fieldsInfo
val res1:Map[String,Class[?]=Map(bossId->long,id->int)

我没有立即明白为什么它不起作用。可能是因为
Expr.apply
如何将值提升到表达式中……但是有没有理由不使用
Map[String,Class[\u]]
呢?@Jasper-M我第一次尝试使用
Map[String,Class[\u]]
确实如此,但宏编译失败,出现以下错误
没有引用类型的隐式参数。ToExpr[Map[String,Class[?]]]]
这就是我将所有内容都转换为Any的原因。我建议解决此问题:哇,这太棒了。谢谢!
    val result: Map[String, Class[Any]] = Map(
      "bossId" -> classOf[scala.Long].asInstanceOf[Class[Any]],
      "id" -> classOf[scala.Int].asInstanceOf[Class[Any]]
    )
    Expr(result)