我正在使用一个返回Tuple2的RightFolder,并希望返回_1
部分。第一个版本rightFoldUntupled1
工作正常但使用了额外的IsComposite
类型类。
在第二个版本rightFoldUntupled2
中,我尝试通过将IsComposite
解构为P
来实现相同而不Product2[_, Values]
。这不再起作用 - 编译器很高兴看到P是Product2[_,_]
,但只要我为_1
使用命名类型参数,它就不会编译任何更多。知道为什么吗?
完整的源代码(sbt准备好〜以隐式调试输出运行)在这里:https://github.com/mpollmeier/shapeless-playground/tree/f3cf049
case class Label[A](name: String)
val label1 = Label[Int]("a")
val labels = label1 :: HNil
object getValue extends Poly2 {
implicit def atLabel[A, B <: HList] = at[Label[A], (B, Map[String, Any])] {
case (label, (acc, values)) ⇒
(values(label.name).asInstanceOf[A] :: acc, values)
}
}
// compiles fine
val untupled1: Int :: HNil = rightFoldUntupled1(labels)
// [error] could not find implicit value for parameter folder:
// shapeless.ops.hlist.RightFolder.Aux[shapeless.::[Main.DestructureTupleTest.Label[Int],shapeless.HNil],
//(shapeless.HNil, Map[String,Any]),Main.DestructureTupleTest.getValue.type,P]
val untupled2: Int :: HNil = rightFoldUntupled2(labels)
def rightFoldUntupled1[L <: HList, P <: Product2[_, _], Values <: HList](labels: L)(
implicit folder: RightFolder.Aux[L, (HNil, Map[String, Any]), getValue.type, P],
ic: IsComposite.Aux[P, Values, _]
): Values = {
val state = Map("a" -> 5, "b" -> "five")
val resultTuple = labels.foldRight((HNil: HNil, state))(getValue)
ic.head(resultTuple)
}
def rightFoldUntupled2[L <: HList, Values, P <: Product2[_, Values]](labels: L)(
implicit folder: RightFolder.Aux[L, (HNil, Map[String, Any]), getValue.type, P]
): Values = {
val state = Map("a" -> 5, "b" -> "five")
val resultTuple = labels.foldRight((HNil: HNil, state))(getValue)
resultTuple._1
}
答案 0 :(得分:4)
这应与rightFoldUntupled1
:
def rightFoldUntupled2[L <: HList, Values, M](labels: L)(
implicit folder: RightFolder.Aux[L, (HNil, Map[String, Any]), getValue.type, (Values, M)]
): Values = {
val state = Map("a" -> 5, "b" -> "five")
val resultTuple = labels.foldRight((HNil: HNil, state))(getValue)
resultTuple._1
}