diff options
author | Josh Suereth <Joshua.Suereth@gmail.com> | 2012-08-10 06:15:11 -0700 |
---|---|---|
committer | Josh Suereth <Joshua.Suereth@gmail.com> | 2012-08-10 06:15:11 -0700 |
commit | cf6fcedece439421df7e4a88e40e74473684753c (patch) | |
tree | a81e082f558857a156d4248233f2c3e0e31e4f86 /src | |
parent | f1806a02feb16c61f6c32e00390703eb3d2ed60b (diff) | |
parent | e62248c510ca04d4d3592baf311dd8ace92ea50d (diff) | |
download | scala-cf6fcedece439421df7e4a88e40e74473684753c.tar.gz scala-cf6fcedece439421df7e4a88e40e74473684753c.tar.bz2 scala-cf6fcedece439421df7e4a88e40e74473684753c.zip |
Merge pull request #1108 from rklaehn/SI-5879
Ensure that a.merged(b)(null) always chooses a in case of collisions
Diffstat (limited to 'src')
-rw-r--r-- | src/library/scala/collection/immutable/HashMap.scala | 32 |
1 files changed, 18 insertions, 14 deletions
diff --git a/src/library/scala/collection/immutable/HashMap.scala b/src/library/scala/collection/immutable/HashMap.scala index 2cf9985523..0b297aeb45 100644 --- a/src/library/scala/collection/immutable/HashMap.scala +++ b/src/library/scala/collection/immutable/HashMap.scala @@ -72,19 +72,8 @@ class HashMap[A, +B] extends AbstractMap[A, B] } private[collection] def computeHash(key: A) = improve(elemHashCode(key)) - - protected type MergeFunction[A1, B1] = ((A1, B1), (A1, B1)) => (A1, B1); - - import HashMap.Merger - protected def liftMerger[A1, B1](mergef: MergeFunction[A1, B1]): Merger[A1, B1] = if (mergef == null) null else new Merger[A1, B1] { - self => - def apply(kv1: (A1, B1), kv2: (A1, B1)): (A1, B1) = mergef(kv1, kv2) - val invert: Merger[A1, B1] = new Merger[A1, B1] { - def apply(kv1: (A1, B1), kv2: (A1, B1)): (A1, B1) = mergef(kv2, kv1) - def invert: Merger[A1, B1] = self - } - } + import HashMap.{Merger, MergeFunction, liftMerger} private[collection] def get0(key: A, hash: Int, level: Int): Option[B] = None @@ -130,11 +119,26 @@ class HashMap[A, +B] extends AbstractMap[A, B] */ object HashMap extends ImmutableMapFactory[HashMap] with BitOperations.Int { - private[immutable] abstract class Merger[A, B] { + private abstract class Merger[A, B] { def apply(kv1: (A, B), kv2: (A, B)): (A, B) def invert: Merger[A, B] } - + + private type MergeFunction[A1, B1] = ((A1, B1), (A1, B1)) => (A1, B1) + + private def liftMerger[A1, B1](mergef: MergeFunction[A1, B1]): Merger[A1, B1] = + if (mergef == null) defaultMerger.asInstanceOf[Merger[A1, B1]] else liftMerger0(mergef) + + private[this] val defaultMerger : Merger[Any, Any] = liftMerger0((a,b) => a) + + private[this] def liftMerger0[A1, B1](mergef: MergeFunction[A1, B1]): Merger[A1, B1] = new Merger[A1, B1] { + self => + def apply(kv1: (A1, B1), kv2: (A1, B1)): (A1, B1) = mergef(kv1, kv2) + val invert: Merger[A1, B1] = new Merger[A1, B1] { + def apply(kv1: (A1, B1), kv2: (A1, B1)): (A1, B1) = mergef(kv2, kv1) + def invert: Merger[A1, B1] = self + } + } /** $mapCanBuildFromInfo */ implicit def canBuildFrom[A, B]: CanBuildFrom[Coll, (A, B), HashMap[A, B]] = new MapCanBuildFrom[A, B] |