diff options
-rw-r--r-- | src/compiler/scala/tools/nsc/matching/CodeFactory.scala | 8 | ||||
-rw-r--r-- | src/compiler/scala/tools/nsc/symtab/StdNames.scala | 1 | ||||
-rw-r--r-- | src/library/scala/List.scala | 39 | ||||
-rw-r--r-- | src/library/scala/Seq.scala | 5 | ||||
-rw-r--r-- | src/library/scala/Stream.scala | 9 |
5 files changed, 31 insertions, 31 deletions
diff --git a/src/compiler/scala/tools/nsc/matching/CodeFactory.scala b/src/compiler/scala/tools/nsc/matching/CodeFactory.scala index c33e9f0e25..48d8297d5d 100644 --- a/src/compiler/scala/tools/nsc/matching/CodeFactory.scala +++ b/src/compiler/scala/tools/nsc/matching/CodeFactory.scala @@ -144,8 +144,8 @@ trait CodeFactory { final def seqHasLength(sel: Tree, ntpe: Type, i: Int) = typed( Equals( - Apply(Select(sel, ntpe.member(nme.length)), List()), - Literal(Constant(i)) + Apply(Select(sel, ntpe.member(nme.lengthCompare)), List(Literal(Constant(i)))), + Literal(Constant(0)) ) )/*defs.Seq_length ?*/ @@ -153,8 +153,8 @@ trait CodeFactory { */ final def seqLongerThan(sel:Tree, tpe:Type, i:Int) = GreaterThanOrEquals( - typed(Apply(Select(sel, tpe.member(nme.length)), List())), - typed(Literal(Constant(i)))) + typed(Apply(Select(sel, tpe.member(nme.lengthCompare)), List(Literal(Constant(i))))), + typed(Literal(Constant(0)))) //defs.Seq_length instead of tpe.member ? final def Not(arg:Tree) = arg match { diff --git a/src/compiler/scala/tools/nsc/symtab/StdNames.scala b/src/compiler/scala/tools/nsc/symtab/StdNames.scala index 51b76bd637..5cc4bd2542 100644 --- a/src/compiler/scala/tools/nsc/symtab/StdNames.scala +++ b/src/compiler/scala/tools/nsc/symtab/StdNames.scala @@ -292,6 +292,7 @@ trait StdNames { val java = newTermName("java") val lang = newTermName("lang") val length = newTermName("length") + val lengthCompare = newTermName("lengthCompare") val lift_ = newTermName("lift") val map = newTermName("map") val n = newTermName("n") diff --git a/src/library/scala/List.scala b/src/library/scala/List.scala index 9fd43f5140..8cc9e4e419 100644 --- a/src/library/scala/List.scala +++ b/src/library/scala/List.scala @@ -401,6 +401,15 @@ sealed abstract class List[+A] extends Seq[A] { */ def head: A + + /** returns length - l, without calling length + */ + override def lengthCompare(l: Int) = { + if (isEmpty) 0 - l + else if (l <= 0) 1 + else tail.lengthCompare(l - 1) + } + /** Returns this list without its first element. * * @return this list without its first element. @@ -1210,32 +1219,8 @@ case object Nil extends List[Nothing] { * @version 1.0, 15/07/2003 */ @SerialVersionUID(0L - 8476791151983527571L) -final case class ::[B](private[scala] var hd: B, private[scala] var tl: List[B]) extends List[B] { - /* XXX: making hd a class-private var crashes the compiler. */ - def head : B = hd - def tail : List[B] = tl +final case class ::[B](hd: B, private[scala] var tl: List[B]) extends List[B] { + def head = hd + def tail = tl override def isEmpty: Boolean = false - - import java.io._ - - private def writeObject(out : ObjectOutputStream) = { - val i = elements - while (i.hasNext) out.writeObject(i.next) - out.writeObject(ListSerializeEnd) - } - private def readObject(in : ObjectInputStream) : Unit = { - hd = in.readObject.asInstanceOf[B] - assert(hd != ListSerializeEnd) - var current : ::[B] = this - while (true) in.readObject match { - case ListSerializeEnd => current.tl = Nil; return - case a : Any => - val list : ::[B] = new ::(a.asInstanceOf[B], Nil) - current.tl = list - current = list - } - } } -/** Only used for list serialization */ -@SerialVersionUID(0L - 8476791151975527571L) -private[scala] case object ListSerializeEnd
\ No newline at end of file diff --git a/src/library/scala/Seq.scala b/src/library/scala/Seq.scala index b78c3f9123..dd59ddfa81 100644 --- a/src/library/scala/Seq.scala +++ b/src/library/scala/Seq.scala @@ -156,6 +156,11 @@ trait Seq[+A] extends AnyRef with PartialFunction[Int, A] with Collection[A] { */ def length: Int + /** Returns length - l. This method is used by matching streams against right-ignoring (...,_*) patterns. + * Lazy sequences should override this method if length forces evaluation of the stream. + */ + def lengthCompare(l: Int): Int = length - l + /** should always be <code>length</code> */ def size = length diff --git a/src/library/scala/Stream.scala b/src/library/scala/Stream.scala index 14bfd258d6..51c96b3f0c 100644 --- a/src/library/scala/Stream.scala +++ b/src/library/scala/Stream.scala @@ -196,6 +196,15 @@ trait Stream[+A] extends Seq.Projection[A] { /** The length of this stream */ override def length: Int = if (isEmpty) 0 else tail.length + 1 + + /** returns length - l without calling length + */ + override def lengthCompare(l: Int) = { + if (isEmpty) 0 - l + else if (l <= 0) 1 + else tail.lengthCompare(l - 1) + } + override def hasDefiniteSize = false |