diff options
author | Paul Phillips <paulp@improving.org> | 2011-06-12 20:08:48 +0000 |
---|---|---|
committer | Paul Phillips <paulp@improving.org> | 2011-06-12 20:08:48 +0000 |
commit | e0155ce582d5ff14c1f560e598ad74948cc0b35d (patch) | |
tree | 6c8db75dc19d9c894342d2eaa2f1806474b91228 | |
parent | 5b09130d85459bc848acadf862757cab54bfa9d2 (diff) | |
download | scala-e0155ce582d5ff14c1f560e598ad74948cc0b35d.tar.gz scala-e0155ce582d5ff14c1f560e598ad74948cc0b35d.tar.bz2 scala-e0155ce582d5ff14c1f560e598ad74948cc0b35d.zip |
Revert r24960, "Change Types#narrow to create a...
Revert r24960, "Change Types#narrow to create an existential rather than
a refinement type."
For many days I have been haunted by the knowledge that the 20 seconds
I took off quick.comp between r24893 and r24920 all came roaring back
around r24960 for no reason which I could discern. To verify r24960 was
not at fault I had compared it against r24959 more than once, and the
difference was negligible.
It was negligible, that is, until I compared under -optimise, and then
the wheels came off. In fact the differences there are so spectacular
(quick.lib under -optimise goes from 8:50 to 4:26 with this patch,
quick.comp from 8:34 to 6:30) that there must be some major disconnect
between what the benchmark charts are measuring and what I am measuring.
In any case, the charts and I do agree on the direction of the arrow.
For reasons which remain to be determined, this commit was bad on the
nanos. Review by odersky.
-rw-r--r-- | src/compiler/scala/reflect/internal/Types.scala | 15 | ||||
-rw-r--r-- | src/compiler/scala/tools/nsc/matching/MatrixAdditions.scala | 18 |
2 files changed, 16 insertions, 17 deletions
diff --git a/src/compiler/scala/reflect/internal/Types.scala b/src/compiler/scala/reflect/internal/Types.scala index cb3ec1bfeb..3264c34d4b 100644 --- a/src/compiler/scala/reflect/internal/Types.scala +++ b/src/compiler/scala/reflect/internal/Types.scala @@ -79,6 +79,8 @@ trait Types /*extends reflect.generic.Types*/ { self: SymbolTable => private var explainSwitch = false private final val emptySymbolSet = immutable.Set.empty[Symbol] + private final val alternativeNarrow = false + private final val LogPendingSubTypesThreshold = 50 private final val LogPendingBaseTypesThreshold = 50 private final val LogVolatileThreshold = 50 @@ -338,12 +340,21 @@ trait Types /*extends reflect.generic.Types*/ { self: SymbolTable => /** Map to a singleton type which is a subtype of this type. * The fallback implemented here gives - * T.narrow = T' forSome { type T' <: T with Singleton } + * T.narrow = (T {}).this.type * Overridden where we know more about where types come from. + * + * todo: change to singleton type of an existentially defined variable + * of the right type instead of making this a `this` of a refined type. */ def narrow: Type = if (phase.erasedTypes) this - else commonOwner(this) freshExistential ".type" setInfo singletonBounds(this) tpe + else if (alternativeNarrow) { // investigate why this does not work! + val tparam = commonOwner(this) freshExistential ".type" setInfo singletonBounds(this) + tparam.tpe + } else { + val cowner = commonOwner(this) + refinedType(List(this), cowner, EmptyScope, cowner.pos).narrow + } /** For a TypeBounds type, itself; * for a reference denoting an abstract type, its bounds, diff --git a/src/compiler/scala/tools/nsc/matching/MatrixAdditions.scala b/src/compiler/scala/tools/nsc/matching/MatrixAdditions.scala index 2d31281e34..d75670fd38 100644 --- a/src/compiler/scala/tools/nsc/matching/MatrixAdditions.scala +++ b/src/compiler/scala/tools/nsc/matching/MatrixAdditions.scala @@ -142,23 +142,11 @@ trait MatrixAdditions extends ast.TreeDSL { import Flags.{ MUTABLE, ABSTRACT, SEALED } private case class Combo(index: Int, sym: Symbol) { + val isBaseClass = sym.tpe.baseClasses.toSet + // is this combination covered by the given pattern? def isCovered(p: Pattern) = { - def coversSym = { - val lhs = decodedEqualsType(p.tpe) - val rhs = sym.tpe - // This logic, arrived upon after much struggle, attempts to find the - // the route through the type maze which let us issue precise exhaustiveness - // warnings against narrowed types (see test case sealed-java-enums.scala) - // while retaining the necessary pattern matching behavior that case _: List[_] => - // matches both "object Nil" and "class ::[T]". - // - // Doubtless there is a more direct/correct expression of it. - if (rhs.typeSymbol.isSingletonExistential) - lhs <:< rhs - else - rhs.baseClasses contains lhs.typeSymbol - } + def coversSym = isBaseClass(decodedEqualsType(p.tpe).typeSymbol) cond(p.tree) { case _: UnApply | _: ArrayValue => true |