gpt4 book ai didi

scala - 将 Magnolia 与 Circe 的自动推导技巧相结合

转载 作者:行者123 更新时间:2023-12-02 04:29:24 25 4
gpt4 key购买 nike

我有一个类型类,想为用户提供半自动和自动派生。我有 a working implementation基于 Magnolia它真的很好用。有一个特性为 Typeclass[A]combine[A]dispatch[A] 提供定义,然后两种类型的推导都可以使用

final object semiauto extends Derivation {
def deriveFormat[A]: Typeclass[A] = macro Magnolia.gen[A]
}

final object auto extends Derivation {
implicit def deriveFormat[A]: Typeclass[A] = macro Magnolia.gen[A]
}

没什么奇怪的。不足为奇的是,当用户将 auto._ 纳入范围时,它会掩盖为特定类型编写的高效派生。

我希望我可以使用 Travis Brown 为 Circe 设计的相同技术,它基本上是这样工作的:

定义一个可以容纳任何值的占位符值类

case class Exported[A](instance: A) extends AnyVal

当我的类型类的值在范围内时,为我的类型类提供低优先级自动派生

object DynamoFormat extends LowPriorityDerivation {
// derivation for specific types
...
}

trait LowPriorityDerivation {
implicit def deriveExported[A](implicit e: Exported[DynamoFormat[A]]) =
e.instance
}

最后,在auto中隐藏导出对象的自动派生

final object auto extends Derivation {
implicit def derive[A]: Exported[DynamoFormat[A]] =
Exported(semiauto.deriveFormat[A])
}

遗憾的是在尝试调用宏时出现编译错误:

magnolia: could not infer auto.Typeclass for type com.gu.scanamo.DynamoFormat[A]
Exported(deriveDynamoFormat[A])
^

我已经看这段代码太久了,我找不到出路;任何帮助将不胜感激。

最佳答案

也许你可以用一个宏来包装它

object MacroWrap {

def typeName[T]: String = macro typeNameImpl[T]

def typeNameImpl[T: c.WeakTypeTag](c: blackbox.Context): c.universe.Tree = {
import c.universe._
q"${c.weakTypeOf[T].toString}"
}

def typeNameWeak[T]: String = macro typeNameWeakImpl[T]

def typeNameWeakImpl[T: c.WeakTypeTag](c: blackbox.Context) = {
import c.universe._
q"${reify(MacroWrap)}.typeName[${weakTypeOf[T]}]"
}
}

//测试

println(MacroWrap.typeNameWeak[String]) // will print String

关于scala - 将 Magnolia 与 Circe 的自动推导技巧相结合,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50544041/

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