gpt4 book ai didi

scala - 从函数的返回值中提取符号

转载 作者:行者123 更新时间:2023-12-01 09:32:01 25 4
gpt4 key购买 nike

我想使用宏来获得引用案例类数据树的字段和子字段的 Symbol 的通用解决方案。

灵感来自 this gist ,我创建了以下骨架:

import language.experimental.macros
import reflect.runtime.universe._
import reflect.macros.Context

object SubRef {

case class SubRef[ SourceT, TargetT ]( symbol : Symbol )

implicit def functionToSubRef
[ SourceT, TargetT ]
( f : SourceT => TargetT )
: SubRef[ SourceT, TargetT ]
= macro functionToSubRefMacro[ SourceT, TargetT ]

def functionToSubRefMacro
[ SourceT : c.WeakTypeTag, TargetT : c.WeakTypeTag ]
( c : Context )
( f : c.Expr[ SourceT => TargetT ] )
: c.Expr[ SubRef[ SourceT, TargetT ] ]
= ???

}

我希望这个解决方案能像这样工作:

case class A( b : B )
case class B( c : Int )

val ref : SubRef[ A, Int ] = _.b.c

如果传入函数,宏转换应该失败:

  • 不是单个表达式
  • 不返回符号的值,它是源符号的子字段,即 targetSymbol.owner[.owner...] == sourceSymbol

缺少的宏实现应该是什么?

最佳答案

除了 Simon 指出您的符号在 2.10 中不起作用之外,编写此宏应该很容易。看起来您已经知道如何执行验证,所以我将省略该部分。

这里真正的挑战是将编译时反射工件 (c.universe.Symbol) 转换为运行时反射工件 (ru.Symbol)。这可以通过具体化来完成。已经有 c.reifyTreec.reifyType,它们对树和类型执行此操作,但 c.reifySymbol 尚不存在。

幸运的是符号具体化应该很容易实现。只需将您的符号包装在一个 Ident 中,即编写 Ident(sym),然后在结果上调用 c.reifyTree。然后在运行时,您只需从包装树中提取一个符号即可。

附言现在我没有时间编写完成所有这些事情的代码。如果你们中的任何人实现了宏并发布了代码,我会很乐意删除我的答案并给你投票:)

关于scala - 从函数的返回值中提取符号,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15351697/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com