我是scala宏的新手,我花了几天时间试着写第一篇。 我有quasiquotes连接问题。
有一个案例条款清单,让我们说以下内容:
val cases = cq"x => 1 " :: cq"_ => 0 " :: Nil
我需要从中构建一个部分功能。 问题是我不知道如何将它们粘贴到最终的quasiquote中。 文档说我应该做这样的事情:
q"{ case ..$cases }"
但如果我这样做,它就无法运作。
有没有办法从这样的列表构建PartialFunction?
感谢您的帮助。
答案 0 :(得分:3)
以下适用于2.11.2:
import scala.reflect.macros.Context
object Macros {
def partial: PartialFunction[Int, Int] = macro partialImpl
def partialImpl(c: Context): c.Expr[PartialFunction[Int, Int]]= {
import c.universe._
val cases = cq"x => 1 " :: cq"_ => 0 " :: Nil
val pf = q"{ case ..$cases } : PartialFunction[Int, Int]"
c.Expr[PartialFunction[Int, Int]](pf)
}
}
然后,您可以拨打Macros.partial(1)
,或Macros.partial.isDefinedAt(2)
。
请注意,为了完成这项工作,我必须在quasiquote PartialFunction[Int, Int]
中明确使用q"{ case ..$cases } : PartialFunction[Int, Int]"
。没有明确的类型定义它没有工作(否则假定为PartialFunction[Any, Int]
)。
Here是部分函数的quasiquote语法规范。它作为一个纯语法树工作,但显然不能被宏解释为除PartialFunction[Any, T]
以外的类型表达式,除非该类型是显式的。