aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMartin Odersky <odersky@gmail.com>2013-11-14 18:27:17 +0100
committerMartin Odersky <odersky@gmail.com>2013-11-14 18:27:17 +0100
commit7ca40215f51a7a008dd1856b9813eabfd8121d8d (patch)
tree59150b0c23ed3ca2c3f170bf43f4c3973011da39
parentffe9e2237956d167b51c9ab1e571a04163b525f7 (diff)
downloaddotty-7ca40215f51a7a008dd1856b9813eabfd8121d8d.tar.gz
dotty-7ca40215f51a7a008dd1856b9813eabfd8121d8d.tar.bz2
dotty-7ca40215f51a7a008dd1856b9813eabfd8121d8d.zip
Making as seenfrom reduce types.
Adding operattions select, derivedSelect which reduce combinations of typerefs over refinement types.
-rw-r--r--src/dotty/tools/dotc/core/TypeOps.scala22
-rw-r--r--src/dotty/tools/dotc/core/Types.scala32
2 files changed, 22 insertions, 32 deletions
diff --git a/src/dotty/tools/dotc/core/TypeOps.scala b/src/dotty/tools/dotc/core/TypeOps.scala
index 8d05a4324..c48a8e715 100644
--- a/src/dotty/tools/dotc/core/TypeOps.scala
+++ b/src/dotty/tools/dotc/core/TypeOps.scala
@@ -20,26 +20,12 @@ trait TypeOps { this: Context =>
toPrefix(pre.baseType(cls).normalizedPrefix, cls.owner, thiscls)
}
- ctx.debugTraceIndented(s"$tp.asSeenFrom($pre, $cls)") { // !!! DEBUG
+ ctx.conditionalTraceIndented(TypeOps.track , s"asSeen ${tp.show} from (${pre.show}, ${cls.show})", show = true) { // !!! DEBUG
tp match {
case tp: NamedType =>
val sym = tp.symbol
if (sym.isStatic) tp
- else {
- val tp1 = tp.derivedNamedType(asSeenFrom(tp.prefix, pre, cls, theMap))
- // Here's an explanation why we short-circuit instantiated type parameters.
- // Say you have This is translated to:
- //
- // class List[type T] ==> class List { type T; val hd: T }
- // xs: List[Int] ==> List { type T = Int }
- //
- // Then with the line above, xs.hd would have type xs.T
- //
- // But in Scala 2.x, its type is Int, which is the dealiased version
- // of xs.T. With the logic below, we get the same outcome as for 2.x.
- if ((tp1 ne tp) && (sym is (TypeParam, butNot = Deferred))) tp1.dealias // todo: why not TypeArgument?
- else tp1
- }
+ else tp.derivedSelect(asSeenFrom(tp.prefix, pre, cls, theMap))
case ThisType(thiscls) =>
toPrefix(pre, cls, thiscls)
case _: BoundType | NoPrefix =>
@@ -179,3 +165,7 @@ trait TypeOps { this: Context =>
}
}
+object TypeOps {
+
+ var track = false // !!!DEBUG
+}
diff --git a/src/dotty/tools/dotc/core/Types.scala b/src/dotty/tools/dotc/core/Types.scala
index 14ebba57d..03b55736c 100644
--- a/src/dotty/tools/dotc/core/Types.scala
+++ b/src/dotty/tools/dotc/core/Types.scala
@@ -679,18 +679,18 @@ object Types {
}
/** The type <this . name> , reduced if possible */
- def typeSelect(name: TypeName)(implicit ctx: Context): Type =
- lookupRefined(this, name) orElse TypeRef(this, name)
+ def select(name: Name)(implicit ctx: Context): Type = {
+ val res = lookupRefined(this, name)
+ if (res.exists) res else NamedType(this, name)
+ }
/** The type <this . name> with given symbol, reduced if possible */
- def typeSelect(name: TypeName, sym: TypeSymbol)(implicit ctx: Context): Type =
- lookupRefined(this, name) orElse TypeRef.withSym(this, name, sym)
-
- /** The type <this . sym> , reduced if possible */
- def typeSelect(sym: TypeSymbol)(implicit ctx: Context): Type =
- typeSelect(sym.name, sym)
+ def select(sym: Symbol)(implicit ctx: Context): Type = {
+ val res = lookupRefined(this, sym.name)
+ if (res.exists) res else NamedType.withSym(this, sym)
+ }
- private def lookupRefined(pre: Type, name: TypeName)(implicit ctx: Context): Type = pre.stripTypeVar match {
+ private def lookupRefined(pre: Type, name: Name)(implicit ctx: Context): Type = pre.stripTypeVar match {
case pre: RefinedType =>
if (pre.refinedName ne name) lookupRefined(pre.parent, name)
else pre.refinedInfo match {
@@ -1456,6 +1456,10 @@ object Types {
if (prefix eq this.prefix) this
else newLikeThis(prefix)
+ def derivedSelect(prefix: Type)(implicit ctx: Context): Type =
+ if (prefix eq this.prefix) this
+ else prefix select this.name
+
/** Create a NamedType of the same kind as this type, if possible,
* but with a new prefix. For HasFixedSym instances another such
* instance is only created if the symbol's owner is a base class of
@@ -2335,12 +2339,8 @@ object Types {
/** Map this function over given type */
def mapOver(tp: Type): Type = tp match {
- case tp: TypeRef =>
- val tp1 = tp.reduceTypeRef
- if (tp1 ne tp) this(tp1) else tp.derivedNamedType(this(tp.prefix))
-
- case tp: TermRef =>
- tp.derivedNamedType(this(tp.prefix))
+ case tp: NamedType =>
+ tp.derivedSelect(this(tp.prefix))
case _: ThisType
| _: BoundType => tp
@@ -2444,7 +2444,7 @@ object Types {
def foldOver(x: T, tp: Type): T = tp match {
case tp: TypeRef =>
- val tp1 = tp.reduceTypeRef
+ val tp1 = tp.reduceTypeRef // !!! needed?
this(x, if (tp1 ne tp) tp1 else tp.prefix)
case tp: TermRef =>