2

访问 Scala 宏中的参数值时的编译问题之后,我想定义一个应用谓词的宏。如果存在语句 fn = c.eval( pred ),则客户端代码无法编译,而没有任何关于问题性质的指示。

def fnInvocation( value : Int, pred : c.Expr[ Int => Boolean ] ): Boolean = fnInvocationImpl

def fnInvocationImpl(c: Context)( value : Int, pred : c.Expr[ Int => Boolean ] ) : c.Expr[Boolean] = {
    var fn = x => x % 2 == 0
    //    fn = c.eval( pred ) // client compilation fails if this line is included
    val result = fn( value )
    c.literal( result )
}

我应该能够从宏中执行此操作吗?

4

1 回答 1

1

宏方法本身没有初始上下文参数列表,它们具有表达式参数是没有意义的。另一方面,在他们的实现中,每个参数(在带有上下文的初始参数列表之后)必须是一个表达式。

在您的情况下,签名需要如下所示:

def fnInvocation(value: Int, pred: Int => Boolean): Boolean =
  macro fnInvocationImpl

def fnInvocationImpl(c: Context)(
  value: c.Expr[Int],
  pred: c.Expr[Int => Boolean]
): c.Expr[Boolean] = ???

我之前回答中的评论也适用于此。如果两个参数都是编译时文字,您可以在编译时执行应用程序——请参阅我的要点here ,了解此类事情如何与函数文字一起使用的示例。如果它们不是两个字面量,您可以构建一个在运行时执行应用程序的树。您甚至可以检查参数是否都是文字,应用函数并返回编译时文字,否则返回生成树。如果值不是文字,您不能做的是在编译时执行应用程序。

于 2013-08-31T11:15:42.517 回答