summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/library/scala/Boxed.scala18
-rw-r--r--src/library/scala/BoxingConversions.scala5
-rw-r--r--src/library/scala/collection/generic/RowFactory.scala49
-rw-r--r--src/library/scala/collection/mutable/FlatArray.scala150
-rw-r--r--test/files/run/Meter.scala33
5 files changed, 176 insertions, 79 deletions
diff --git a/src/library/scala/Boxed.scala b/src/library/scala/Boxed.scala
deleted file mode 100644
index 6055b3f436..0000000000
--- a/src/library/scala/Boxed.scala
+++ /dev/null
@@ -1,18 +0,0 @@
-/* __ *\
-** ________ ___ / / ___ Scala API **
-** / __/ __// _ | / / / _ | (c) 2002-2011, LAMP/EPFL **
-** __\ \/ /__/ __ |/ /__/ __ | http://www.scala-lang.org/ **
-** /____/\___/_/ |_/____/_/ | | **
-** |/ **
-\* */
-
-package scala
-
-/** A trait that can be implemented by user-defined value classes
- */
-trait Boxed[Unboxed] extends Any {
-
- /** The underlying value wrapped by the value class */
- def unbox: Unboxed
-}
-
diff --git a/src/library/scala/BoxingConversions.scala b/src/library/scala/BoxingConversions.scala
new file mode 100644
index 0000000000..fd1bd6c121
--- /dev/null
+++ b/src/library/scala/BoxingConversions.scala
@@ -0,0 +1,5 @@
+package scala
+abstract class BoxingConversions[Boxed, Unboxed] {
+ def box(x: Unboxed): Boxed
+ def unbox(x: Boxed): Unboxed
+}
diff --git a/src/library/scala/collection/generic/RowFactory.scala b/src/library/scala/collection/generic/RowFactory.scala
deleted file mode 100644
index c1559c9397..0000000000
--- a/src/library/scala/collection/generic/RowFactory.scala
+++ /dev/null
@@ -1,49 +0,0 @@
-package scala.collection
-package generic
-
-import mutable.{Builder, ArrayBuffer}
-import scala.specialized
-
-/** A factory class for rows -- flat arrays of value classes that use the unboxed representation
- * of the element type.
- *
- */
-abstract class RowFactory[@specialized Unboxed: ClassManifest, Boxed <: scala.Boxed[Unboxed]] extends (Unboxed => Boxed) { box =>
-
- /** Convert to boxed representation
- */
- def apply(x: Unboxed): Boxed
-
- class Row(elems: Array[Unboxed]) extends mutable.IndexedSeq[Boxed] with mutable.IndexedSeqLike[Boxed, Row] {
-
- override protected[this] def newBuilder: Builder[Boxed, Row] = Row.newBuilder
-
- def apply(idx: Int): Boxed = box(elems(idx))
-
- def update(idx: Int, elem: Boxed): Unit = elems(idx) = elem.unbox
-
- def length = elems.length
-
- override def foreach[U](f: Boxed => U): Unit = elems foreach (elem => f(box(elem)))
-
- }
-
- object Row {
- def fromSeq(elems: Seq[Boxed]): Row = {
- val xs: Array[Unboxed] = new Array[Unboxed](elems.length)
- var i = 0
- for (elem <- elems) { xs(i) = elem.unbox; i += 1 }
- new Row(xs)
- }
-
- def apply(elems: Boxed*) = fromSeq(elems)
-
- def newBuilder: Builder[Boxed, Row] = new ArrayBuffer mapResult fromSeq
-
- implicit def canBuildFrom: CanBuildFrom[Row, Boxed, Row] =
- new CanBuildFrom[Row, Boxed, Row] {
- def apply(): Builder[Boxed, Row] = newBuilder
- def apply(from: Row): Builder[Boxed, Row] = newBuilder
- }
- }
-}
diff --git a/src/library/scala/collection/mutable/FlatArray.scala b/src/library/scala/collection/mutable/FlatArray.scala
new file mode 100644
index 0000000000..0650d09861
--- /dev/null
+++ b/src/library/scala/collection/mutable/FlatArray.scala
@@ -0,0 +1,150 @@
+/* __ *\
+** ________ ___ / / ___ Scala API **
+** / __/ __// _ | / / / _ | (c) 2002-2011, LAMP/EPFL **
+** __\ \/ /__/ __ |/ /__/ __ | http://scala-lang.org/ **
+** /____/\___/_/ |_/____/_/ | | **
+** |/ **
+\* */
+
+
+
+package scala.collection
+package mutable
+
+import scala.reflect.ClassManifest
+import generic.CanBuildFrom
+
+/**
+ * A class representing `Array[T]`.
+ *
+ * @tparam T type of the elements in this wrapped array.
+ *
+ * @author Martin Odersky, Stephane Micheloud
+ * @version 1.0
+ * @since 2.8
+ * @define Coll WrappedArray
+ * @define coll wrapped array
+ * @define orderDependent
+ * @define orderDependentFold
+ * @define mayNotTerminateInf
+ * @define willNotTerminateInf
+ */
+abstract sealed class FlatArray[T]
+extends AbstractSeq[T]
+ with IndexedSeq[T]
+ with IndexedSeqOptimized[T, FlatArray[T]]
+{
+
+ override protected[this] def thisCollection: FlatArray[T] = this
+ override protected[this] def toCollection(repr: FlatArray[T]): FlatArray[T] = repr
+
+ /** The length of the array */
+ def length: Int
+
+ /** The element at given index */
+ def apply(index: Int): T
+
+ /** Update element at given index */
+ def update(index: Int, elem: T): Unit
+
+ override def stringPrefix = "FlatArray"
+
+ override protected[this] def newBuilder: Builder[T, FlatArray[T]] = ??? // implemented in FlatArray.Impl
+
+ /** Clones this object, including the underlying Array. */
+ override def clone: FlatArray[T] = ??? // implemented in FlatArray.Impl
+}
+
+
+/** A companion object used to create instances of `WrappedArray`.
+ */
+object FlatArray {
+
+ def empty[Boxed, Unboxed](elems: Boxed*)
+ (implicit boxings: BoxingConversions[Boxed, Unboxed], elemManifest: ClassManifest[Unboxed]): FlatArray[Boxed] = apply()
+
+ def apply[Boxed, Unboxed](elems: Boxed*)
+ (implicit boxings: BoxingConversions[Boxed, Unboxed], elemManifest: ClassManifest[Unboxed]): FlatArray[Boxed] = {
+ val b = newBuilder[Boxed, Unboxed]
+ b.sizeHint(elems.length)
+ b ++= elems
+ b.result
+ }
+
+ def newBuilder[Boxed, Unboxed]
+ (implicit boxings: BoxingConversions[Boxed, Unboxed], elemManifest: ClassManifest[Unboxed]): Builder[Boxed, FlatArray[Boxed]] =
+ new Bldr[Boxed, Unboxed](boxings, elemManifest)
+
+ implicit def canBuildFrom[Boxed, Unboxed](
+ implicit
+ boxings: BoxingConversions[Boxed, Unboxed],
+ elemManifest: ClassManifest[Unboxed]): CanBuildFrom[FlatArray[_], Boxed, FlatArray[Boxed]] =
+ new CanBuildFrom[FlatArray[_], Boxed, FlatArray[Boxed]] {
+ def apply(from: FlatArray[_]): Builder[Boxed, FlatArray[Boxed]] =
+ newBuilder[Boxed, Unboxed]
+ def apply: Builder[Boxed, FlatArray[Boxed]] =
+ newBuilder[Boxed, Unboxed]
+ }
+
+ private class Bldr[Boxed, Unboxed](boxings: BoxingConversions[Boxed, Unboxed], manifest: ClassManifest[Unboxed]) extends Builder[Boxed, FlatArray[Boxed]] {
+
+ private var elems: Array[Unboxed] = _
+ private var capacity: Int = 0
+ private var size: Int = 0
+
+ private def resize(size: Int) {
+ val newelems = manifest.newArray(size)
+ if (this.size > 0) Array.copy(elems, 0, newelems, 0, this.size)
+ elems = newelems
+ capacity = size
+ }
+
+ override def sizeHint(size: Int) {
+ if (capacity < size) resize(size)
+ }
+
+ private def ensureSize(size: Int) {
+ if (capacity < size) {
+ var newsize = if (capacity == 0) 16 else capacity * 2
+ while (newsize < size) newsize *= 2
+ resize(newsize)
+ }
+ }
+
+ def +=(elem: Boxed): this.type = {
+ ensureSize(size + 1)
+ elems(size) = boxings.unbox(elem)
+ size += 1
+ this
+ }
+
+ def clear() {
+ size = 0
+ }
+
+ def result(): FlatArray[Boxed] = {
+ if (capacity == 0 || capacity != size) resize(size)
+ new FlatArray.Impl(elems, boxings, manifest)
+ }
+ }
+
+ private class Impl[Boxed, Unboxed](
+ elems: Array[Unboxed],
+ boxings: BoxingConversions[Boxed, Unboxed],
+ elemManifest: ClassManifest[Unboxed]) extends FlatArray[Boxed] {
+
+ def length = elems.length
+
+ def apply(idx: Int): Boxed = boxings.box(elems(idx))
+
+ def update(idx: Int, elem: Boxed) = elems(idx) = boxings.unbox(elem)
+
+ /** Creates new builder for this collection ==> move to subclasses
+ */
+ override protected[this] def newBuilder: Builder[Boxed, FlatArray[Boxed]] =
+ new Bldr[Boxed, Unboxed](boxings, elemManifest)
+
+ /** Clones this object, including the underlying Array. */
+ override def clone: FlatArray[Boxed] = new Impl[Boxed, Unboxed](elems.clone(), boxings, elemManifest)
+ }
+}
diff --git a/test/files/run/Meter.scala b/test/files/run/Meter.scala
index 15d35054a2..936b8d98b7 100644
--- a/test/files/run/Meter.scala
+++ b/test/files/run/Meter.scala
@@ -1,17 +1,21 @@
-import collection.generic.RowFactory
-
-class Meter(val unbox: Double) extends AnyVal with Boxed[Double] with Printable {
+class Meter(val underlying: Double) extends AnyVal with Printable {
def + (other: Meter): Meter =
- new Meter(this.unbox + other.unbox)
- def / (other: Meter): Double = this.unbox / other.unbox
- def / (factor: Double): Meter = new Meter(this.unbox / factor)
- def < (other: Meter): Boolean = this.unbox < other.unbox
- override def toString: String = unbox.toString+"m"
+ new Meter(this.underlying + other.underlying)
+ def / (other: Meter): Double = this.underlying / other.underlying
+ def / (factor: Double): Meter = new Meter(this.underlying / factor)
+ def < (other: Meter): Boolean = this.underlying < other.underlying
+ override def toString: String = underlying.toString+"m"
}
-object Meter extends RowFactory[Double, Meter] {
+object Meter extends (Double => Meter) {
+
def apply(x: Double): Meter = new Meter(x)
-}
+ implicit val boxings = new BoxingConversions[Meter, Double] {
+ def box(x: Double) = new Meter(x)
+ def unbox(m: Meter) = m.underlying
+ }
+
+}
trait Printable extends Any { def print: Unit = Console.print(this) }
object Test extends App {
@@ -55,14 +59,19 @@ object Test extends App {
}
{ println("testing wrapped arrays")
- val arr = Meter.Row(x, y + x)
+ import collection.mutable.FlatArray
+ val arr = FlatArray(x, y + x)
println(arr)
- def foo(x: Meter.Row) {
+ def foo(x: FlatArray[Meter]) {
for (i <- 0 until x.length) { x(i).print; println(" "+x(i)) }
}
val m = arr(0)
println(m)
foo(arr)
+ val ys: Seq[Meter] = arr map (_ + new Meter(1))
+ println(ys)
+ val zs = arr map (_ / Meter(1))
+ println(zs)
}
}