diff options
-rw-r--r-- | src/library/scala/collection/generic/GenericTraversableTemplate.scala | 12 | ||||
-rw-r--r-- | test/files/run/transpose.scala | 12 |
2 files changed, 23 insertions, 1 deletions
diff --git a/src/library/scala/collection/generic/GenericTraversableTemplate.scala b/src/library/scala/collection/generic/GenericTraversableTemplate.scala index 6a1bff6cec..d6f01718ff 100644 --- a/src/library/scala/collection/generic/GenericTraversableTemplate.scala +++ b/src/library/scala/collection/generic/GenericTraversableTemplate.scala @@ -12,6 +12,7 @@ package scala.collection package generic import mutable.Builder +import annotation.migration import annotation.unchecked.uncheckedVariance /** A template class for companion objects of ``regular`` collection classes @@ -136,18 +137,27 @@ trait GenericTraversableTemplate[+A, +CC[X] <: Traversable[X]] extends HasNewBui * element type of this $coll is a `Traversable`. * @return a two-dimensional $coll of ${coll}s which has as ''n''th row * the ''n''th column of this $coll. + * @throws `IllegalArgumentException` if all collections in this $coll + * are not of the same size. */ + @migration(2, 9, "As of 2.9, transpose throws an exception if collections are not uniformly sized.") def transpose[B](implicit asTraversable: A => /*<:<!!!*/ TraversableOnce[B]): CC[CC[B] @uncheckedVariance] = { if (isEmpty) return genericBuilder[CC[B]].result - val bs: IndexedSeq[Builder[B, CC[B]]] = IndexedSeq.fill(asTraversable(head).size)(genericBuilder[B]) + def fail = throw new IllegalArgumentException("transpose requires all collections have the same size") + + val headSize = asTraversable(head).size + val bs: IndexedSeq[Builder[B, CC[B]]] = IndexedSeq.fill(headSize)(genericBuilder[B]) for (xs <- this) { var i = 0 for (x <- asTraversable(xs)) { + if (i >= headSize) fail bs(i) += x i += 1 } + if (i != headSize) + fail } val bb = genericBuilder[CC[B]] for (b <- bs) bb += b.result diff --git a/test/files/run/transpose.scala b/test/files/run/transpose.scala new file mode 100644 index 0000000000..2761a24ff5 --- /dev/null +++ b/test/files/run/transpose.scala @@ -0,0 +1,12 @@ +object Test { + def wrap[T >: Null](body: => T) = + try body + catch { case _: IllegalArgumentException => null } + + def main(args: Array[String]): Unit = { + assert(wrap(Nil.transpose) == Nil) + assert(wrap(List(List(1, 2), List(1)).transpose) == null) + assert(wrap(List(List(1), List(1, 2)).transpose) == null) + assert(wrap(List(List(1, 2), List(1, 2)).transpose) == List(List(1, 1), List(2, 2))) + } +} |