@@ -1264,7 +1264,23 @@ class TypeComparer(initctx: Context) extends DotClass with ConstraintHandling {
1264
1264
case tp1 : RefinedType =>
1265
1265
tp2 match {
1266
1266
case tp2 : RefinedType if tp1.refinedName == tp2.refinedName =>
1267
- tp1.derivedRefinedType(tp1.parent & tp2.parent, tp1.refinedName, tp1.refinedInfo & tp2.refinedInfo)
1267
+ // Given two refinements `T1 { X = S1 }` and `T2 { X = S2 }`, if `S1 =:= S2`
1268
+ // (possibly by instantiating type parameters), rewrite to `T1 & T2 { X = S1 }`.
1269
+ // Otherwise rewrite to `T1 & T2 { X B }` where `B` is the conjunction of
1270
+ // the bounds of `X` in `T1` and `T2`.
1271
+ // The first rule above is contentious because it cuts the constraint set.
1272
+ // But without it we would replace the two aliases by
1273
+ // `T { X >: S1 | S2 <: S1 & S2 }`, which looks weird and is probably
1274
+ // not what's intended.
1275
+ val rinfo1 = tp1.refinedInfo
1276
+ val rinfo2 = tp2.refinedInfo
1277
+ val parent = tp1.parent & tp2.parent
1278
+ val rinfo =
1279
+ if (rinfo1.isAlias && rinfo2.isAlias && isSameType(rinfo1, rinfo2))
1280
+ rinfo1
1281
+ else
1282
+ rinfo1 & rinfo2
1283
+ tp1.derivedRefinedType(parent, tp1.refinedName, rinfo)
1268
1284
case _ =>
1269
1285
NoType
1270
1286
}
@@ -1528,7 +1544,7 @@ class ExplainingTypeComparer(initctx: Context) extends TypeComparer(initctx) {
1528
1544
}
1529
1545
1530
1546
override def addConstraint (param : PolyParam , bound : Type , fromBelow : Boolean ): Boolean =
1531
- traceIndented(i " add constraint $param ${if (fromBelow) " >:" else " <:" } $bound $frozenConstraint" ) {
1547
+ traceIndented(i " add constraint $param ${if (fromBelow) " >:" else " <:" } $bound $frozenConstraint, constraint = ${ctx.typerState.constraint} " ) {
1532
1548
super .addConstraint(param, bound, fromBelow)
1533
1549
}
1534
1550
0 commit comments