@@ -366,6 +366,12 @@ object desugar {
366
366
(if (args.isEmpty) tycon else AppliedTypeTree (tycon, args))
367
367
.withPos(cdef.pos.startPos)
368
368
369
+ def isHK (tparam : Tree ): Boolean = tparam match {
370
+ case TypeDef (_, LambdaTypeTree (tparams, body)) => true
371
+ case TypeDef (_, rhs : DerivedTypeTree ) => isHK(rhs.watched)
372
+ case _ => false
373
+ }
374
+
369
375
def appliedRef (tycon : Tree , tparams : List [TypeDef ] = constrTparams, widenHK : Boolean = false ) = {
370
376
val targs = for (tparam <- tparams) yield {
371
377
val targ = refOfDef(tparam)
@@ -467,18 +473,29 @@ object desugar {
467
473
// ev1: Eq[T1$1, T1$2], ..., evn: Eq[Tn$1, Tn$2]])
468
474
// : Eq[C[T1$, ..., Tn$1], C[T1$2, ..., Tn$2]] = Eq
469
475
//
470
- // If any of the T_i are higher-kinded, say `Ti[X1 >: L1 <: U1, ..., Xm >: Lm <: Um]`,
471
- // the corresponding type parameters for $ev_i are `Ti$1[_, ..., _], Ti$2[_, ..., _]`
472
- // (with m underscores `_`).
476
+ // Higher-kinded type arguments `Ti` are omitted as evidence parameters.
477
+ //
478
+ // FIXME: This is too simplistic. Instead of just generating evidence arguments
479
+ // for every first-kinded type parameter, we should look instead at the
480
+ // actual types occurring in cases and derive parameters from these. E.g. in
481
+ //
482
+ // enum HK[F[_]] {
483
+ // case C1(x: F[Int]) extends HK[F[Int]]
484
+ // case C2(y: F[String]) extends HL[F[Int]]
485
+ //
486
+ // we would need evidence parameters for `F[Int]` and `F[String]`
487
+ // We should generate Eq instances with the techniques
488
+ // of typeclass derivation once that is available.
473
489
def eqInstance = {
474
490
val leftParams = constrTparams.map(derivedTypeParam(_, " $1" ))
475
491
val rightParams = constrTparams.map(derivedTypeParam(_, " $2" ))
476
- val subInstances = (leftParams, rightParams).zipped.map((param1, param2) =>
477
- appliedRef(ref(defn.EqType ), List (param1, param2), widenHK = true ))
492
+ val subInstances =
493
+ for ((param1, param2) <- leftParams `zip` rightParams if ! isHK(param1))
494
+ yield appliedRef(ref(defn.EqType ), List (param1, param2), widenHK = true )
478
495
DefDef (
479
496
name = nme.eqInstance,
480
497
tparams = leftParams ++ rightParams,
481
- vparamss = List (makeImplicitParameters(subInstances)),
498
+ vparamss = if (subInstances.isEmpty) Nil else List (makeImplicitParameters(subInstances)),
482
499
tpt = appliedTypeTree(ref(defn.EqType ),
483
500
appliedRef(classTycon, leftParams) :: appliedRef(classTycon, rightParams) :: Nil ),
484
501
rhs = ref(defn.EqModule .termRef)).withFlags(Synthetic | Implicit )
0 commit comments