summaryrefslogtreecommitdiff
path: root/sources
diff options
context:
space:
mode:
authorburaq <buraq@epfl.ch>2004-08-19 17:17:55 +0000
committerburaq <buraq@epfl.ch>2004-08-19 17:17:55 +0000
commit9b178df043a2eeb447bb33d338cdaac8c7a0d33f (patch)
treeecb01a1e9fb8bf663426cade24f70c108abe7a23 /sources
parent751b5fef76494d6ef22a6e95734c88a7bb7dc8a8 (diff)
downloadscala-9b178df043a2eeb447bb33d338cdaac8c7a0d33f.tar.gz
scala-9b178df043a2eeb447bb33d338cdaac8c7a0d33f.tar.bz2
scala-9b178df043a2eeb447bb33d338cdaac8c7a0d33f.zip
files for io, used by xml parsing
Diffstat (limited to 'sources')
-rw-r--r--sources/scala/io/Position.scala84
-rw-r--r--sources/scala/io/Source.scala121
2 files changed, 205 insertions, 0 deletions
diff --git a/sources/scala/io/Position.scala b/sources/scala/io/Position.scala
new file mode 100644
index 0000000000..4fb57b9dc7
--- /dev/null
+++ b/sources/scala/io/Position.scala
@@ -0,0 +1,84 @@
+/* __ *\
+** ________ ___ / / ___ Scala API **
+** / __/ __// _ | / / / _ | (c) 2003-2004, LAMP/EPFL **
+** __\ \/ /__/ __ |/ /__/ __ | **
+** /____/\___/_/ |_/____/_/ | | **
+** |/ **
+** $Id$
+\* */
+
+package scala.io;
+
+/** convenience methods to encode line and column number in one
+ * single integer. The encode line (column)
+ * numbers range from 0 to LINE_MASK (COLUMN_MASK), where 0 indicates
+ * that the line (column) is the undefined and 1 represents the first
+ * line (column). Line (Column) numbers greater than LINE_MASK
+ * (COLUMN_MASK) are replaced by LINE_MASK (COLUMN_MASK). Furthermore,
+ * if the encoded line number is LINE_MASK, the column number is
+ * always set to 0.
+
+ * The following properties hold:
+ * - the undefined position is 0: encode(0,0) == 0
+ * - encodings are non-negative : encode(line,column) >= 0
+ * - position order is preserved:
+ * (line1 < line2) || (line1 == line2 && column1 < column2)
+ * implies
+ * encode(line1,column1) <= encode(line2,column2)
+ * @author Burak Emir (translated from work by Matthias Zengers and others)
+ */
+object Position {
+
+ /** Number of bits used to encode the line number */
+ final val LINE_BITS = 20;
+ /** Number of bits used to encode the column number */
+ final val COLUMN_BITS = 31 - LINE_BITS; // no negatives => 31
+
+ /** Mask to decode the line number */
+ final val LINE_MASK = (1 << LINE_BITS) - 1;
+ /** Mask to decode the column number */
+ final val COLUMN_MASK = (1 << COLUMN_BITS) - 1;
+
+ /** The undefined position */
+ final val NOPOS = 0;
+
+ /** The first position in a source file */
+ final val FIRSTPOS = encode(1, 1);
+
+ //########################################################################
+ // Public Functions
+
+ /** Encodes a position into a single integer. */
+ final def encode(line: Int, column: Int): Int = {
+ var line1, column1 = 0;
+ if( line < 0 )
+ error(line+" < 0");
+ if(( line == 0 )&&(column != 0))
+ error(line+","+column+" not allowed");
+ if( column < 0 )
+ error(line+","+column+" not allowed");
+
+ if (line >= LINE_MASK) { line1 = LINE_MASK; column1 = 0; }
+ if (column > COLUMN_MASK) column1 = COLUMN_MASK;
+ (line1 << COLUMN_BITS) | column1;
+ }
+
+ /** Returns the line number of the encoded position. */
+ final def line(pos: Int): Int = {
+ (pos >> COLUMN_BITS) & LINE_MASK;
+ }
+
+ /** Returns the column number of the encoded position. */
+ final def column(pos: Int): Int = {
+ pos & COLUMN_MASK;
+ }
+
+ /** Returns a string representation of the encoded position. */
+ def toString(pos: Int): String = {
+ val sb = new StringBuffer();
+ sb.append(line(pos));
+ sb.append(':');
+ sb.append(column(pos));
+ sb.toString();
+ }
+}
diff --git a/sources/scala/io/Source.scala b/sources/scala/io/Source.scala
new file mode 100644
index 0000000000..8c22e2f3bf
--- /dev/null
+++ b/sources/scala/io/Source.scala
@@ -0,0 +1,121 @@
+/* __ *\
+** ________ ___ / / ___ Scala API **
+** / __/ __// _ | / / / _ | (c) 2003-2004, LAMP/EPFL **
+** __\ \/ /__/ __ |/ /__/ __ | **
+** /____/\___/_/ |_/____/_/ | | **
+** |/ **
+** $Id$
+\* */
+
+package scala.io;
+
+/** convenience methods to create an iterable representation of a source file
+ * @author Burak Emir
+ */
+object Source {
+
+ /** creates Source from array of bytes, with empty description
+ */
+ def fromBytes(bytes: Array[Byte]): Source =
+ fromString(new String(bytes));
+
+ /** creates Source from array of bytes with given encoding, with empty description
+ */
+ def fromBytes(bytes: Array[Byte], enc: String): Source =
+ fromString(new String(bytes, enc));
+
+ /** creates Source from array of characters, with empty description
+ */
+ def fromChars(chars: Array[Char]): Source = {
+ val it = Iterator.fromArray(chars);
+ new Source {
+ val iter = it;
+ }
+ }
+ /** creates Source from string, with empty description
+ */
+ def fromString(s: String): Source = {
+ val it = Iterator.fromString(s);
+ new Source {
+ val iter = it;
+ }
+ }
+
+ /** creates Source from file with given name, setting its description to
+ * filename.
+ */
+ def fromFile(name: String): Source =
+ fromFile( new java.io.File( name ));
+
+ /** creates Source from file with given name, using given encoding, setting
+ * its description to filename.
+ */
+ def fromFile(name: String, enc: String): Source =
+ fromFile( new java.io.File( name ), enc);
+
+ /** creates Source from file, using default character encoding, setting its
+ * description to filename.
+ */
+ def fromFile(file: java.io.File): Source = {
+ val arr: Array[Byte] = new Array[Byte]( file.length().asInstanceOf[Int] );
+ val is = new java.io.FileInputStream( file );
+ is.read( arr );
+ val s = fromBytes(arr);
+ s.descr = file.getName();
+ s
+ }
+
+ /** creates Source from file, using given character encoding, setting its
+ * description to filename.
+ */
+ def fromFile(file: java.io.File, enc: String): Source = {
+ val arr: Array[Byte] = new Array[Byte]( file.length().asInstanceOf[Int] );
+ val is = new java.io.FileInputStream( file );
+ is.read( arr );
+ val s = fromBytes(arr, enc);
+ s.descr = file.getName();
+ s
+ }
+}
+
+/** an iterable representation of source files.
+ * @author Burak Emir
+ */
+abstract class Source extends Iterator[Char] {
+ /** default col increment for tabs '\t', set to 4 */
+ val tabinc = 4;
+
+ val iter: Iterator[Char];
+ /** returns next characters, updates positions and assigns the character
+ * ch as side effect
+ */
+ def next = {
+ ch = iter.next;
+ pos = Position.encode(cline,ccol);
+ ch match {
+ case '\n' =>
+ ccol = 1;
+ cline = cline + 1;
+ case '\t' =>
+ ccol = ccol + tabinc;
+ case _ =>
+ ccol = ccol + 1;
+ }
+ ch
+ };
+ /** returns true if this source has more characters
+ */
+ def hasNext = iter.hasNext;
+
+ var cline = 1;
+ var ccol = 1;
+ /** position of last character returned by next*/
+ var pos = 0;
+
+ /** the last character returned by next.
+ * the value before the first call to next is undefined
+ */
+ var ch: Char = _;
+ /** description of this source */
+ var descr:String = "";
+}