diff options
author | Mike Skells <mike.skells@talk21.com> | 2017-01-25 22:36:08 +0000 |
---|---|---|
committer | Adriaan Moors <adriaan@lightbend.com> | 2017-01-28 14:00:34 -0800 |
commit | d540bf01fe4d9e5c56a68b0d3bada9d97af77e3f (patch) | |
tree | 8176ccf542af74edd5ef15f01a51f31095a7d54a | |
parent | 4f9faff9370fb7b5ceb767204bca309075a1a62d (diff) | |
download | scala-d540bf01fe4d9e5c56a68b0d3bada9d97af77e3f.tar.gz scala-d540bf01fe4d9e5c56a68b0d3bada9d97af77e3f.tar.bz2 scala-d540bf01fe4d9e5c56a68b0d3bada9d97af77e3f.zip |
Optimize slice and take in ArrayOps, WrappedArray
use Array block copy operations rather than builder/iterator
-rw-r--r-- | bincompat-backward.whitelist.conf | 41 | ||||
-rw-r--r-- | bincompat-forward.whitelist.conf | 296 | ||||
-rw-r--r-- | src/library/scala/collection/mutable/ArrayOps.scala | 74 | ||||
-rw-r--r-- | src/library/scala/collection/mutable/WrappedArray.scala | 49 |
4 files changed, 450 insertions, 10 deletions
diff --git a/bincompat-backward.whitelist.conf b/bincompat-backward.whitelist.conf index 0770b3cb95..7303e8d80f 100644 --- a/bincompat-backward.whitelist.conf +++ b/bincompat-backward.whitelist.conf @@ -223,6 +223,47 @@ filter { { matchName="scala.concurrent.impl.Promise.toString" problemName=MissingMethodProblem + }, + // https://github.com/scala/scala/pull/5652 + { + matchName="scala.collection.mutable.ArrayOps#ofChar.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofShort.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofUnit.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofInt.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofBoolean.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofDouble.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofRef.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofByte.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofLong.slice" + problemName=FinalMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofFloat.slice" + problemName=FinalMethodProblem } ] } diff --git a/bincompat-forward.whitelist.conf b/bincompat-forward.whitelist.conf index 7f28a718bd..023e3bddac 100644 --- a/bincompat-forward.whitelist.conf +++ b/bincompat-forward.whitelist.conf @@ -628,6 +628,302 @@ filter { { matchName="scala.reflect.api.SerializedTypeTag.serialVersionUID" problemName=MissingFieldProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofChar" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofChar.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofChar.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofShort" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofShort.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofShort.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofByte.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofByte.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofBoolean.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofBoolean.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofChar.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofChar.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofDouble.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofDouble.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofUnit" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofUnit.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofUnit.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofInt.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofInt.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofInt" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofInt.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofInt.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofRef.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofRef.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofChar.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofChar.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofUnit.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofUnit.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofBoolean" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofBoolean.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofBoolean.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofShort.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofShort.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofShort.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofShort.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray.slice" + problemName=IncompatibleResultTypeProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofRef.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofRef.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofUnit.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofUnit.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofByte.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofByte.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofDouble.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofDouble.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOpsImpl" + problemName=MissingClassProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofInt.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofInt.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofDouble" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofDouble.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofDouble.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofRef" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofRef.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofRef.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofLong.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofLong.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofByte" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofByte.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofByte.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofFloat.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofFloat.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofLong.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofLong.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofBoolean.sliceImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofBoolean.emptyImpl$extension" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofFloat.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.WrappedArray#ofFloat.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofLong" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofLong.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofLong.emptyImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps$ofFloat" + problemName=MissingTypesProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofFloat.sliceImpl" + problemName=DirectMissingMethodProblem + }, + { + matchName="scala.collection.mutable.ArrayOps#ofFloat.emptyImpl" + problemName=DirectMissingMethodProblem } ] } diff --git a/src/library/scala/collection/mutable/ArrayOps.scala b/src/library/scala/collection/mutable/ArrayOps.scala index 00491ef20e..04bb1074ea 100644 --- a/src/library/scala/collection/mutable/ArrayOps.scala +++ b/src/library/scala/collection/mutable/ArrayOps.scala @@ -10,6 +10,8 @@ package scala package collection package mutable +import java.util + import scala.compat.Platform.arraycopy import scala.reflect.ClassTag import scala.runtime.ScalaRunTime._ @@ -175,6 +177,23 @@ trait ArrayOps[T] extends Any with ArrayLike[T, Array[T]] with CustomParalleliza } +/** to provide binary compat for 2.11 and 2.12 this class contains + * functionality that should be migrated to ArrayOps in 2.13 + * + */ +private[mutable] sealed trait ArrayOpsImpl[T] extends Any with ArrayOps[T] { + override final def slice(from: Int, until: Int): Array[T] = { + val start = if (from < 0) 0 else from + if (until <= start || start >= repr.length) + return emptyImpl + val end = if (until > length) length else until + sliceImpl(start, end) + } + protected def emptyImpl: Array[T] + protected def sliceImpl(from: Int, until: Int): Array[T] + +} + /** * A companion object for `ArrayOps`. * @@ -182,12 +201,24 @@ trait ArrayOps[T] extends Any with ArrayLike[T, Array[T]] with CustomParalleliza */ object ArrayOps { + private val emptyByteArray = new Array[Byte](0) + private val emptyShortArray = new Array[Short](0) + private val emptyIntArray = new Array[Int](0) + private val emptyLongArray = new Array[Long](0) + private val emptyFloatArray = new Array[Float](0) + private val emptyDoubleArray = new Array[Double](0) + private val emptyUnitArray = new Array[Unit](0) + private val emptyCharArray = new Array[Char](0) + private val emptyBooleanArray = new Array[Boolean](0) + /** A class of `ArrayOps` for arrays containing reference types. */ - final class ofRef[T <: AnyRef](override val repr: Array[T]) extends AnyVal with ArrayOps[T] with ArrayLike[T, Array[T]] { + final class ofRef[T <: AnyRef](override val repr: Array[T]) extends AnyVal with ArrayOpsImpl[T] with ArrayLike[T, Array[T]] { override protected[this] def thisCollection: WrappedArray[T] = new WrappedArray.ofRef[T](repr) override protected[this] def toCollection(repr: Array[T]): WrappedArray[T] = new WrappedArray.ofRef[T](repr) override protected[this] def newBuilder = new ArrayBuilder.ofRef[T]()(ClassTag[T](arrayElementClass(repr.getClass))) + protected override def emptyImpl:Array[T] = util.Arrays.copyOf[T](repr,0) + protected override def sliceImpl(from: Int, until: Int): Array[T] = util.Arrays.copyOfRange[T](repr, from, until) def length: Int = repr.length def apply(index: Int): T = repr(index) @@ -195,11 +226,13 @@ object ArrayOps { } /** A class of `ArrayOps` for arrays containing `byte`s. */ -final class ofByte(override val repr: Array[Byte]) extends AnyVal with ArrayOps[Byte] with ArrayLike[Byte, Array[Byte]] { +final class ofByte(override val repr: Array[Byte]) extends AnyVal with ArrayOpsImpl[Byte] with ArrayLike[Byte, Array[Byte]] { override protected[this] def thisCollection: WrappedArray[Byte] = new WrappedArray.ofByte(repr) override protected[this] def toCollection(repr: Array[Byte]): WrappedArray[Byte] = new WrappedArray.ofByte(repr) override protected[this] def newBuilder = new ArrayBuilder.ofByte + protected override def emptyImpl = emptyByteArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Byte = repr(index) @@ -207,11 +240,13 @@ final class ofByte(override val repr: Array[Byte]) extends AnyVal with ArrayOps[ } /** A class of `ArrayOps` for arrays containing `short`s. */ -final class ofShort(override val repr: Array[Short]) extends AnyVal with ArrayOps[Short] with ArrayLike[Short, Array[Short]] { +final class ofShort(override val repr: Array[Short]) extends AnyVal with ArrayOpsImpl[Short] with ArrayLike[Short, Array[Short]] { override protected[this] def thisCollection: WrappedArray[Short] = new WrappedArray.ofShort(repr) override protected[this] def toCollection(repr: Array[Short]): WrappedArray[Short] = new WrappedArray.ofShort(repr) override protected[this] def newBuilder = new ArrayBuilder.ofShort + protected override def emptyImpl = emptyShortArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Short = repr(index) @@ -219,11 +254,13 @@ final class ofShort(override val repr: Array[Short]) extends AnyVal with ArrayOp } /** A class of `ArrayOps` for arrays containing `char`s. */ -final class ofChar(override val repr: Array[Char]) extends AnyVal with ArrayOps[Char] with ArrayLike[Char, Array[Char]] { +final class ofChar(override val repr: Array[Char]) extends AnyVal with ArrayOpsImpl[Char] with ArrayLike[Char, Array[Char]] { override protected[this] def thisCollection: WrappedArray[Char] = new WrappedArray.ofChar(repr) override protected[this] def toCollection(repr: Array[Char]): WrappedArray[Char] = new WrappedArray.ofChar(repr) override protected[this] def newBuilder = new ArrayBuilder.ofChar + protected override def emptyImpl = emptyCharArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Char = repr(index) @@ -231,11 +268,13 @@ final class ofChar(override val repr: Array[Char]) extends AnyVal with ArrayOps[ } /** A class of `ArrayOps` for arrays containing `int`s. */ -final class ofInt(override val repr: Array[Int]) extends AnyVal with ArrayOps[Int] with ArrayLike[Int, Array[Int]] { +final class ofInt(override val repr: Array[Int]) extends AnyVal with ArrayOpsImpl[Int] with ArrayLike[Int, Array[Int]] { override protected[this] def thisCollection: WrappedArray[Int] = new WrappedArray.ofInt(repr) override protected[this] def toCollection(repr: Array[Int]): WrappedArray[Int] = new WrappedArray.ofInt(repr) override protected[this] def newBuilder = new ArrayBuilder.ofInt + protected override def emptyImpl = emptyIntArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Int = repr(index) @@ -243,11 +282,13 @@ final class ofInt(override val repr: Array[Int]) extends AnyVal with ArrayOps[In } /** A class of `ArrayOps` for arrays containing `long`s. */ -final class ofLong(override val repr: Array[Long]) extends AnyVal with ArrayOps[Long] with ArrayLike[Long, Array[Long]] { +final class ofLong(override val repr: Array[Long]) extends AnyVal with ArrayOpsImpl[Long] with ArrayLike[Long, Array[Long]] { override protected[this] def thisCollection: WrappedArray[Long] = new WrappedArray.ofLong(repr) override protected[this] def toCollection(repr: Array[Long]): WrappedArray[Long] = new WrappedArray.ofLong(repr) override protected[this] def newBuilder = new ArrayBuilder.ofLong + protected override def emptyImpl = emptyLongArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Long = repr(index) @@ -255,11 +296,13 @@ final class ofLong(override val repr: Array[Long]) extends AnyVal with ArrayOps[ } /** A class of `ArrayOps` for arrays containing `float`s. */ -final class ofFloat(override val repr: Array[Float]) extends AnyVal with ArrayOps[Float] with ArrayLike[Float, Array[Float]] { +final class ofFloat(override val repr: Array[Float]) extends AnyVal with ArrayOpsImpl[Float] with ArrayLike[Float, Array[Float]] { override protected[this] def thisCollection: WrappedArray[Float] = new WrappedArray.ofFloat(repr) override protected[this] def toCollection(repr: Array[Float]): WrappedArray[Float] = new WrappedArray.ofFloat(repr) override protected[this] def newBuilder = new ArrayBuilder.ofFloat + protected override def emptyImpl = emptyFloatArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Float = repr(index) @@ -267,11 +310,13 @@ final class ofFloat(override val repr: Array[Float]) extends AnyVal with ArrayOp } /** A class of `ArrayOps` for arrays containing `double`s. */ -final class ofDouble(override val repr: Array[Double]) extends AnyVal with ArrayOps[Double] with ArrayLike[Double, Array[Double]] { +final class ofDouble(override val repr: Array[Double]) extends AnyVal with ArrayOpsImpl[Double] with ArrayLike[Double, Array[Double]] { override protected[this] def thisCollection: WrappedArray[Double] = new WrappedArray.ofDouble(repr) override protected[this] def toCollection(repr: Array[Double]): WrappedArray[Double] = new WrappedArray.ofDouble(repr) override protected[this] def newBuilder = new ArrayBuilder.ofDouble + protected override def emptyImpl = emptyDoubleArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Double = repr(index) @@ -279,11 +324,13 @@ final class ofDouble(override val repr: Array[Double]) extends AnyVal with Array } /** A class of `ArrayOps` for arrays containing `boolean`s. */ -final class ofBoolean(override val repr: Array[Boolean]) extends AnyVal with ArrayOps[Boolean] with ArrayLike[Boolean, Array[Boolean]] { +final class ofBoolean(override val repr: Array[Boolean]) extends AnyVal with ArrayOpsImpl[Boolean] with ArrayLike[Boolean, Array[Boolean]] { override protected[this] def thisCollection: WrappedArray[Boolean] = new WrappedArray.ofBoolean(repr) override protected[this] def toCollection(repr: Array[Boolean]): WrappedArray[Boolean] = new WrappedArray.ofBoolean(repr) override protected[this] def newBuilder = new ArrayBuilder.ofBoolean + protected override def emptyImpl = emptyBooleanArray + protected override def sliceImpl(from: Int, until: Int) = util.Arrays.copyOfRange(repr, from, until) def length: Int = repr.length def apply(index: Int): Boolean = repr(index) @@ -291,11 +338,18 @@ final class ofBoolean(override val repr: Array[Boolean]) extends AnyVal with Arr } /** A class of `ArrayOps` for arrays of `Unit` types. */ -final class ofUnit(override val repr: Array[Unit]) extends AnyVal with ArrayOps[Unit] with ArrayLike[Unit, Array[Unit]] { +final class ofUnit(override val repr: Array[Unit]) extends AnyVal with ArrayOpsImpl[Unit] with ArrayLike[Unit, Array[Unit]] { override protected[this] def thisCollection: WrappedArray[Unit] = new WrappedArray.ofUnit(repr) override protected[this] def toCollection(repr: Array[Unit]): WrappedArray[Unit] = new WrappedArray.ofUnit(repr) override protected[this] def newBuilder = new ArrayBuilder.ofUnit + protected override def emptyImpl = emptyUnitArray + protected override def sliceImpl(from: Int, until: Int) = { + // cant use util.Arrays.copyOfRange[Unit](repr, from, until) - Unit is special and doesnt compile + val res = new Array[Unit](until-from) + System.arraycopy(repr, from, res, 0, res.size) + res + } def length: Int = repr.length def apply(index: Int): Unit = repr(index) diff --git a/src/library/scala/collection/mutable/WrappedArray.scala b/src/library/scala/collection/mutable/WrappedArray.scala index 8740bda835..81e0e64fb2 100644 --- a/src/library/scala/collection/mutable/WrappedArray.scala +++ b/src/library/scala/collection/mutable/WrappedArray.scala @@ -72,6 +72,17 @@ extends AbstractSeq[T] else super.toArray[U] } + override def slice(from: Int, until: Int): WrappedArray[T] = { + val start = if (from < 0) 0 else from + if (until <= start || start >= repr.length) + return emptyImpl + val end = if (until > length) length else until + sliceImpl(start, end) + } + //retain existing functionallity for existing implementations outside this file + protected def emptyImpl: WrappedArray[T] = newBuilder.result() + //retain existing functionallity for existing implementations outside this file + protected def sliceImpl(from: Int, until: Int): WrappedArray[T] = super.slice(from, until) override def stringPrefix = "WrappedArray" @@ -88,6 +99,7 @@ extends AbstractSeq[T] /** A companion object used to create instances of `WrappedArray`. */ object WrappedArray { + import java.util // This is reused for all calls to empty. private val EmptyWrappedArray = new ofRef[AnyRef](new Array[AnyRef](0)) def empty[T <: AnyRef]: WrappedArray[T] = EmptyWrappedArray.asInstanceOf[WrappedArray[T]] @@ -121,11 +133,23 @@ object WrappedArray { def newBuilder[A]: Builder[A, IndexedSeq[A]] = new ArrayBuffer + private val emptyWrappedByte = new ofByte(new Array[Byte](0)) + private val emptyWrappedShort = new ofShort(new Array[Short](0)) + private val emptyWrappedInt = new ofInt(new Array[Int](0)) + private val emptyWrappedLong = new ofLong(new Array[Long](0)) + private val emptyWrappedFloat = new ofFloat(new Array[Float](0)) + private val emptyWrappedDouble = new ofDouble(new Array[Double](0)) + private val emptyWrappedUnit = new ofUnit(new Array[Unit](0)) + private val emptyWrappedChar = new ofChar(new Array[Char](0)) + private val emptyWrappedBoolean = new ofBoolean(new Array[Boolean](0)) + final class ofRef[T <: AnyRef](val array: Array[T]) extends WrappedArray[T] with Serializable { lazy val elemTag = ClassTag[T](arrayElementClass(array.getClass)) def length: Int = array.length def apply(index: Int): T = array(index).asInstanceOf[T] def update(index: Int, elem: T) { array(index) = elem } + protected override def emptyImpl = new ofRef(util.Arrays.copyOf[T](array,0)) + protected override def sliceImpl(from: Int, until: Int) = new ofRef[T](util.Arrays.copyOfRange[T](array, from, until)) } final class ofByte(val array: Array[Byte]) extends WrappedArray[Byte] with Serializable { @@ -133,6 +157,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Byte = array(index) def update(index: Int, elem: Byte) { array(index) = elem } + protected override def emptyImpl = emptyWrappedByte + protected override def sliceImpl(from: Int, until: Int) = new ofByte(util.Arrays.copyOfRange(array, from, until)) } final class ofShort(val array: Array[Short]) extends WrappedArray[Short] with Serializable { @@ -140,6 +166,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Short = array(index) def update(index: Int, elem: Short) { array(index) = elem } + protected override def emptyImpl = emptyWrappedShort + protected override def sliceImpl(from: Int, until: Int) = new ofShort(util.Arrays.copyOfRange(array, from, until)) } final class ofChar(val array: Array[Char]) extends WrappedArray[Char] with Serializable { @@ -147,6 +175,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Char = array(index) def update(index: Int, elem: Char) { array(index) = elem } + protected override def emptyImpl = emptyWrappedChar + protected override def sliceImpl(from: Int, until: Int) = new ofChar(util.Arrays.copyOfRange(array, from, until)) } final class ofInt(val array: Array[Int]) extends WrappedArray[Int] with Serializable { @@ -154,6 +184,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Int = array(index) def update(index: Int, elem: Int) { array(index) = elem } + protected override def emptyImpl = emptyWrappedInt + protected override def sliceImpl(from: Int, until: Int) = new ofInt(util.Arrays.copyOfRange(array, from, until)) } final class ofLong(val array: Array[Long]) extends WrappedArray[Long] with Serializable { @@ -161,6 +193,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Long = array(index) def update(index: Int, elem: Long) { array(index) = elem } + protected override def emptyImpl = emptyWrappedLong + protected override def sliceImpl(from: Int, until: Int) = new ofLong(util.Arrays.copyOfRange(array, from, until)) } final class ofFloat(val array: Array[Float]) extends WrappedArray[Float] with Serializable { @@ -168,6 +202,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Float = array(index) def update(index: Int, elem: Float) { array(index) = elem } + protected override def emptyImpl = emptyWrappedFloat + protected override def sliceImpl(from: Int, until: Int) = new ofFloat(util.Arrays.copyOfRange(array, from, until)) } final class ofDouble(val array: Array[Double]) extends WrappedArray[Double] with Serializable { @@ -175,6 +211,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Double = array(index) def update(index: Int, elem: Double) { array(index) = elem } + protected override def emptyImpl = emptyWrappedDouble + protected override def sliceImpl(from: Int, until: Int) = new ofDouble(util.Arrays.copyOfRange(array, from, until)) } final class ofBoolean(val array: Array[Boolean]) extends WrappedArray[Boolean] with Serializable { @@ -182,6 +220,8 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Boolean = array(index) def update(index: Int, elem: Boolean) { array(index) = elem } + protected override def emptyImpl = emptyWrappedBoolean + protected override def sliceImpl(from: Int, until: Int) = new ofBoolean(util.Arrays.copyOfRange(array, from, until)) } final class ofUnit(val array: Array[Unit]) extends WrappedArray[Unit] with Serializable { @@ -189,5 +229,14 @@ object WrappedArray { def length: Int = array.length def apply(index: Int): Unit = array(index) def update(index: Int, elem: Unit) { array(index) = elem } + protected override def emptyImpl = emptyWrappedUnit + protected override def sliceImpl(from: Int, until: Int) = { + // cant use + // new ofUnit(util.Arrays.copyOfRange[Unit](array, from, until)) - Unit is special and doesnt compile + // cant use util.Arrays.copyOfRange[Unit](repr, from, until) - Unit is special and doesnt compile + val res = new Array[Unit](until-from) + System.arraycopy(repr, from, res, 0, until-from) + new ofUnit(res) + } } } |