diff options
author | Martin Odersky <odersky@gmail.com> | 2016-02-04 14:37:44 +0100 |
---|---|---|
committer | Martin Odersky <odersky@gmail.com> | 2016-02-04 14:37:56 +0100 |
commit | 8efdbdc9843f66fbb8fc39aa2716da0fe7187fd9 (patch) | |
tree | 243f8f8ece4db7840291c6ce80414caed284762e /src/dotty/tools/dotc/core/Types.scala | |
parent | 7d1d93e95113802bee77b9d2b89475a56be46bf7 (diff) | |
download | dotty-8efdbdc9843f66fbb8fc39aa2716da0fe7187fd9.tar.gz dotty-8efdbdc9843f66fbb8fc39aa2716da0fe7187fd9.tar.bz2 dotty-8efdbdc9843f66fbb8fc39aa2716da0fe7187fd9.zip |
Try to make refinements match in approximateUnions
See comment in Typer#approximateUnion for an explanation.
Fixes #1045.
Diffstat (limited to 'src/dotty/tools/dotc/core/Types.scala')
-rw-r--r-- | src/dotty/tools/dotc/core/Types.scala | 19 |
1 files changed, 19 insertions, 0 deletions
diff --git a/src/dotty/tools/dotc/core/Types.scala b/src/dotty/tools/dotc/core/Types.scala index e266bab6f..812edf2fe 100644 --- a/src/dotty/tools/dotc/core/Types.scala +++ b/src/dotty/tools/dotc/core/Types.scala @@ -1199,6 +1199,15 @@ object Types { * class B extends C[B] with D with E * * we approximate `A | B` by `C[A | B] with D` + * + * As a second measure we also homogenize refinements containing + * type variables. For instance, if `A` is an instantiatable type variable, + * then + * + * ArrayBuffer[Int] | ArrayBuffer[A] + * + * is approximated by instantiating `A` to `Int` and returning `ArrayBuffer[Int]` + * instead of `ArrayBuffer[_ >: Int | A <: Int & A]` */ def approximateUnion(implicit ctx: Context) = ctx.approximateUnion(this) @@ -2847,6 +2856,11 @@ object Types { case _ => super.| (that) } + /** The implied bounds, where aliases are mapped to intervals from + * Nothing/Any + */ + def boundsInterval(implicit ctx: Context): TypeBounds = this + /** If this type and that type have the same variance, this variance, otherwise 0 */ final def commonVariance(that: TypeBounds): Int = (this.variance + that.variance) / 2 @@ -2884,6 +2898,11 @@ object Types { else if (v < 0) derivedTypeAlias(this.lo & that.lo, v) else super.| (that) } + + override def boundsInterval(implicit ctx: Context): TypeBounds = + if (variance == 0) this + else if (variance < 0) TypeBounds.lower(alias) + else TypeBounds.upper(alias) } class CachedTypeAlias(alias: Type, variance: Int, hc: Int) extends TypeAlias(alias, variance) { |