summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul Phillips <paulp@improving.org>2010-10-19 22:14:29 +0000
committerPaul Phillips <paulp@improving.org>2010-10-19 22:14:29 +0000
commit9bd74024a120aca0c777ee3917084776875daa69 (patch)
tree2ed674dcc5e08e09a9d10eaa468c211af3ac4ffb
parent8b17d54737ba37bc96f91bfcd69590acb3f728e9 (diff)
downloadscala-9bd74024a120aca0c777ee3917084776875daa69.tar.gz
scala-9bd74024a120aca0c777ee3917084776875daa69.tar.bz2
scala-9bd74024a120aca0c777ee3917084776875daa69.zip
A modified approach to map withDefault[Value].
-rw-r--r--src/library/scala/collection/Map.scala24
-rw-r--r--src/library/scala/collection/immutable/Map.scala16
-rw-r--r--src/library/scala/collection/mutable/Map.scala12
-rw-r--r--test/files/run/t3829.scala8
4 files changed, 32 insertions, 28 deletions
diff --git a/src/library/scala/collection/Map.scala b/src/library/scala/collection/Map.scala
index 6841ad14d0..6196093219 100644
--- a/src/library/scala/collection/Map.scala
+++ b/src/library/scala/collection/Map.scala
@@ -6,8 +6,6 @@
** |/ **
\* */
-
-
package scala.collection
import generic._
@@ -30,12 +28,6 @@ import generic._
*/
trait Map[A, +B] extends Iterable[(A, B)] with MapLike[A, B, Map[A, B]] {
def empty: Map[A, B] = Map.empty
-
- /** The same map with a given default function */
- def withDefault[B1 >: B](d: A => B1): Map[A, B1] = new Map.WithDefault[A, B1](this, d)
-
- /** The same map with a given default value */
- def withDefaultValue[B1 >: B](d: B1): Map[A, B1] = new Map.WithDefault[A, B1](this, x => d)
}
/** $factoryInfo
@@ -48,15 +40,13 @@ object Map extends MapFactory[Map] {
/** $mapCanBuildFromInfo */
implicit def canBuildFrom[A, B]: CanBuildFrom[Coll, (A, B), Map[A, B]] = new MapCanBuildFrom[A, B]
- class WithDefault[A, +B](underlying: Map[A, B], d: A => B) extends Map[A, B] {
- override def size = underlying.size
- def get(key: A) = underlying.get(key) orElse Some(default(key))
- def iterator = underlying.iterator
- override def empty = new WithDefault(underlying.empty, d)
- override def updated[B1 >: B](key: A, value: B1): WithDefault[A, B1] = new WithDefault[A, B1](underlying.updated[B1](key, value), d)
- override def + [B1 >: B](kv: (A, B1)): WithDefault[A, B1] = updated(kv._1, kv._2)
- def - (key: A): WithDefault[A, B] = new WithDefault(underlying - key, d)
+ /** An abstract shell used by { mutable, immutable }.Map but not by collection.Map
+ * because of variance issues.
+ */
+ abstract class WithDefault[A, +B](underlying: Map[A, B], d: A => B) extends Map[A, B] {
+ override def size = underlying.size
+ def get(key: A) = underlying.get(key) orElse Some(default(key))
+ def iterator = underlying.iterator
override def default(key: A): B = d(key)
}
-
}
diff --git a/src/library/scala/collection/immutable/Map.scala b/src/library/scala/collection/immutable/Map.scala
index ef1f6b60ed..272caec5ea 100644
--- a/src/library/scala/collection/immutable/Map.scala
+++ b/src/library/scala/collection/immutable/Map.scala
@@ -7,7 +7,6 @@
\* */
-
package scala.collection
package immutable
@@ -32,6 +31,12 @@ trait Map[A, +B] extends Iterable[(A, B)]
override def empty: Map[A, B] = Map.empty
+ /** The same map with a given default function */
+ def withDefault[B1 >: B](d: A => B1): immutable.Map[A, B1] = new Map.WithDefault[A, B1](this, d)
+
+ /** The same map with a given default value */
+ def withDefaultValue[B1 >: B](d: B1): immutable.Map[A, B1] = new Map.WithDefault[A, B1](this, x => d)
+
/** Add a key/value pair to this map.
* @param key the key
* @param value the value
@@ -52,6 +57,15 @@ object Map extends ImmutableMapFactory[Map] {
def empty[A, B]: Map[A, B] = EmptyMap.asInstanceOf[Map[A, B]]
+ class WithDefault[A, +B](underlying: Map[A, B], d: A => B) extends collection.Map.WithDefault[A, B](underlying, d) with Map[A, B] {
+ override def empty = new WithDefault(underlying.empty, d)
+ override def updated[B1 >: B](key: A, value: B1): WithDefault[A, B1] = new WithDefault[A, B1](underlying.updated[B1](key, value), d)
+ override def + [B1 >: B](kv: (A, B1)): WithDefault[A, B1] = updated(kv._1, kv._2)
+ override def - (key: A): WithDefault[A, B] = new WithDefault(underlying - key, d)
+ override def withDefault[B1 >: B](d: A => B1): immutable.Map[A, B1] = new WithDefault[A, B1](underlying, d)
+ override def withDefaultValue[B1 >: B](d: B1): immutable.Map[A, B1] = new WithDefault[A, B1](underlying, x => d)
+ }
+
@serializable
private object EmptyMap extends Map[Any, Nothing] {
override def size: Int = 0
diff --git a/src/library/scala/collection/mutable/Map.scala b/src/library/scala/collection/mutable/Map.scala
index 047db08142..5df8594a16 100644
--- a/src/library/scala/collection/mutable/Map.scala
+++ b/src/library/scala/collection/mutable/Map.scala
@@ -27,10 +27,10 @@ trait Map[A, B]
override def empty: Map[A, B] = Map.empty
/** The same map with a given default function */
- def withDefault(d: A => B): Map[A, B] = new Map.WithDefault[A, B](this, d)
+ def withDefault(d: A => B): mutable.Map[A, B] = new Map.WithDefault[A, B](this, d)
/** The same map with a given default value */
- def withDefaultValue(d: B): Map[A, B] = new Map.WithDefault[A, B](this, x => d)
+ def withDefaultValue(d: B): mutable.Map[A, B] = new Map.WithDefault[A, B](this, x => d)
/** Return a read-only projection of this map. !!! or just use an (immutable) MapProxy?
def readOnly : scala.collection.Map[A, B] = new scala.collection.Map[A, B] {
@@ -63,7 +63,11 @@ object Map extends MutableMapFactory[Map] {
override def updated[B1 >: B](key: A, value: B1): WithDefault[A, B1] = new WithDefault[A, B1](underlying.updated[B1](key, value), d)
override def + [B1 >: B](kv: (A, B1)): WithDefault[A, B1] = updated(kv._1, kv._2)
override def - (key: A): WithDefault[A, B] = new WithDefault(underlying - key, d)
- }
+ /** If these methods aren't overridden to thread through the underlying map,
+ * successive calls to withDefault* have no effect.
+ */
+ override def withDefault(d: A => B): mutable.Map[A, B] = new WithDefault[A, B](underlying, d)
+ override def withDefaultValue(d: B): mutable.Map[A, B] = new WithDefault[A, B](underlying, x => d)
+ }
}
-
diff --git a/test/files/run/t3829.scala b/test/files/run/t3829.scala
index 49fbbe6363..a7d03f34eb 100644
--- a/test/files/run/t3829.scala
+++ b/test/files/run/t3829.scala
@@ -1,13 +1,9 @@
-
-
-
-
// ticket #3829
object Test {
- import collection._
+ import collection.{ mutable, immutable }
def main(args: Array[String]) {
- val map = Map(1 -> 2, 3 -> 4)
+ val map = immutable.Map(1 -> 2, 3 -> 4)
assert(map.get(0) == None)
val defmap = map.withDefaultValue(-1)