Note that there are some explanatory texts on larger screens.

plurals
  1. POMap on HList fails with subtypes of generic type in Scala & Shapeless
    text
    copied!<p>Say we have the following classes and some values (in Scala):</p> <pre><code>class A[T](val x: T) class B[T](x: T, val y: T) extends A[T](x) val x1 = new A("test") val x2 = new B(1,2) val x3 = new B("foo","bar") val x4 = new A(1) </code></pre> <p>Further, we define the following polymorphic function value (using shapeless):</p> <pre><code>object f extends (A ~&gt; Option) { def apply[T](s: A[T]) = Some(s.x) } </code></pre> <p>Now we can call:</p> <pre><code>f(x1); f(x2); f(x3); f(x4) </code></pre> <p>Which all succeed (and should IMHO). However:</p> <pre><code>val list = x1 :: x2 :: x3 :: x4 :: HNil list.map(f) // could not find implicit value for parameter mapper: // shapeless.Mapper[f.type,shapeless.::[A[String],shapeless.::[ // B[Int],shapeless.::[B[String],shapeless.::[A[Int],shapeless.HNil]]]]] </code></pre> <p>Where I was expecting:</p> <pre><code>Some("test") :: Some(1) :: Some("foo") :: Some(1) :: HNil </code></pre> <p>Note that this works:</p> <pre><code>val list2 = x1 :: x4 :: HNil // only instances of A list2.map(f) </code></pre> <p><strong>UPDATE</strong></p> <p>It seems that if we specify each case separately, it's fine:</p> <pre><code>object f extends Poly1 { implicit def caseA[T] = at[A[T]]{s =&gt; Some(s.x)} implicit def caseB[T] = at[B[T]]{s =&gt; Some(s.x)} } </code></pre> <p>However, trying to express this a bit smarter, does not work (not even for simple applications):</p> <pre><code>object f extends Poly1 { implicit def caseA[T, S &lt;: A[T]] = at[S]{s =&gt; Some(s.x)} } </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload