我正在尝试参数化一个需要在可以检索a 的泛型类型A
上工作的方法。LabelledGeneric
这是天真的方法
case class Foo(bar: String, baz: Boolean)
def params[A](a: A) = {
val lbl = LabelledGeneric[A]
val keys = Keys[lbl.Repr].apply
...
}
val myThingy = params(Foo)
当然,底层宏抱怨。它对以下内容了解不够A
:
类型 A 不是类或特征
所以,我试图LabelledGeneric
推断
def params[A](a: A)(implicit lbl: LabelledGeneric[A]) = {
val keys = Keys[lbl.Repr].apply
...
}
这似乎有效,但类型不再Repr
是已知的HList
类型参数 [lbl.Repr] 不符合方法应用的类型参数边界 [L <: shapeless.HList]
好的,让我们尝试更精确
def params[A, Repr <: HList](a: A)(implicit lbl: LabelledGeneric.Aux[A, Repr]) = {
val keys = Keys[lbl.Repr].apply
...
}
现在,Repr
绝对是一个HList
,但仍然Keys
无法解决它的隐含
找不到参数值的隐含值:shapeless.ops.record.Values[lbl.Repr]
最后的尝试,让我们尝试隐式计算我需要的所有内容
def params[A, Repr <: HList](a: A)(implicit
lbl: LabelledGeneric.Aux[A, Repr],
kk: Keys[Repr]
) = {
val keys = kk.apply
...
}
仍然没有运气,显然第一个隐式无法在呼叫现场解决
找不到参数 lbl 的隐式值:shapeless.LabelledGeneric.Aux[example.Main.Foo.type,Repr]
[错误] 参数(Foo)
显然,当直接处理特定类型时,所有这些机器都可以工作,例如
val lbl = LabelledGeneric[Foo]
val keys = Keys[lbl.Repr].apply
// no problem
我显然在方法签名中缺少对我的类型进行的所需改进,但我可以了解这里发生的事情。任何想法?