Shapeless mapping and subtype polymorphism with custom type bound

六月ゝ 毕业季﹏ 提交于 2019-12-07 20:48:23

问题


Trying to map an HList of a custom polymorphic class I'm getting the dreaded "could not find implicit value for parameter mapper" error. A code sample:

import shapeless._

trait SubTrait
case class A() extends SubTrait
case class B() extends SubTrait

case class C[T <: SubTrait](x: T)

object TheMapper extends Poly1 {
  implicit def default[T <: SubTrait, L[T] <: C[T]] = at[L[T]](_.x)
}

val ab = C(A()) :: C(B()) :: HNil

println(ab.map(TheMapper))

This works fine if the bound for L[T] is e.g. Iterable (see this very similar question, solution, and comments). What am I missing?


回答1:


For some reason the real error gets swallowed. If you compile this step by step in the REPL you'll get this error:

error: type arguments [T] do not conform to class C's type parameter bounds [T <: SubTrait]
         implicit def default[T <: SubTrait, L[T] <: C[T]] = at[L[T]](_.x)
                                                     ^

The problem is that the T in L[T] <: C[T] is not the same as the one in T <: SubTrait. It gets more readable if you rename it:

scala> object TheMapper extends Poly1 {
     |   implicit def default[T <: SubTrait, L[x] <: C[x]] = at[L[T]](_.x)
     | }
<console>:18: error: type arguments [x] do not conform to class C's type parameter bounds [T <: SubTrait]
         implicit def default[T <: SubTrait, L[x] <: C[x]] = at[L[T]](_.x)
                                                     ^

The solution is to put a bound on x.

scala> object TheMapper extends Poly1 {
     |   implicit def default[T <: SubTrait, L[x <: SubTrait] <: C[x]] = at[L[T]](_.x)
     | }
defined object TheMapper

scala> val ab = C(A()) :: C(B()) :: HNil
ab: shapeless.::[C[A],shapeless.::[C[B],shapeless.HNil]] = C(A()) :: C(B()) :: HNil

scala> println(ab.map(TheMapper))
A() :: B() :: HNil


来源:https://stackoverflow.com/questions/42853858/shapeless-mapping-and-subtype-polymorphism-with-custom-type-bound

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!