📄 xmlparser.java
字号:
/* kXML
*
* The contents of this file are subject to the Enhydra Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License
* on the Enhydra web site ( http://www.enhydra.org/ ).
*
* Software distributed under the License is distributed on an "AS IS"
* basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
* the License for the specific terms governing rights and limitations
* under the License.
*
* The Initial Developer of kXML is Stefan Haustein. Copyright (C)
* 2000, 2001 Stefan Haustein, D-46045 Oberhausen (Rhld.),
* Germany. All Rights Reserved.
*
* Contributor(s): Paul Palaszewski, Wilhelm Fitzpatrick,
* Eric Foster-Johnson, Michael Angel, Jan Andrle
*
* */
package org.kxml.parser;
import java.io.*;
import java.util.*;
import org.kxml.*;
import org.kxml.io.ParseException;
/** A simple, pull based "Common XML" parser. Attention: This class has
* been renamed from DefaultParser for consitency with the org.kxml.io
* package. */
public class XmlParser extends AbstractXmlParser {
static final String UNEXPECTED_EOF = "Unexpected EOF";
char [] buf;
boolean eof;
int bufPos;
int bufCount;
Reader reader;
boolean relaxed;
int line = 1;
int column = 1;
Vector qNames = new Vector ();
boolean immediateClose = false;
StartTag current;
String closePending;
/** The next event. May be null at startup. */
protected ParseEvent next;
int peekChar () throws IOException {
if (eof) return -1;
if (bufPos >= bufCount) {
if (buf.length == 1) {
int c = reader.read ();
if (c == -1) {
eof = true;
return -1;
}
bufCount = 1;
buf [0] = (char) c;
}
else {
bufCount = reader.read (buf, 0, buf.length);
if (bufCount == -1) {
eof = true;
return -1;
}
}
bufPos = 0;
}
return buf[bufPos];
}
int readChar () throws IOException {
int p = peekChar ();
bufPos++;
column++;
if (p == 10) {
line++;
column = 1;
}
return p;
}
void skipWhitespace () throws IOException {
while (!eof && peekChar () <= ' ')
readChar ();
}
public String readName () throws IOException {
int c = readChar ();
if (c < 128 && c != '_' && c != ':'
&& (c < 'a' || c > 'z')
&& (c < 'A' || c > 'Z'))
throw new DefaultParserException ("name expected!", null);
StringBuffer buf = new StringBuffer ();
buf.append ((char) c);
while (!eof) {
c = peekChar ();
if (c < 128 && c != '_' && c != '-' && c != ':' && c != '.'
&& (c < '0' || c > '9')
&& (c < 'a' || c > 'z')
&& (c < 'A' || c > 'Z'))
break;
buf.append ((char) readChar ());
}
return buf.toString ();
}
/** Reads chars to the given buffer until the given stopChar
* is reached. The stopChar itself is not consumed. */
public StringBuffer readTo (char stopChar,
StringBuffer buf) throws IOException {
while (!eof && peekChar () != stopChar)
buf.append ((char) readChar ());
return buf;
}
/** creates a new Parser based on the give reader */
class DefaultParserException extends ParseException {
DefaultParserException (String msg, Exception chained) {
super (msg, chained, XmlParser.this.line, XmlParser.this.column);
}
}
public XmlParser (Reader reader) throws IOException {
this (reader,
Runtime.getRuntime ().freeMemory () >= 1048576 ? 8192 : 1);
}
public XmlParser (Reader reader, int bufSize) throws IOException {
this.reader = reader; //new LookAheadReader (reader);
buf = new char [bufSize];
}
public String resolveCharacterEntity (String name) throws IOException {
throw new DefaultParserException ("Undefined: &"+name+";", null);
}
/* precondition: <!- consumed */
ParseEvent parseComment () throws IOException {
StringBuffer buf = new StringBuffer ();
if (readChar () != '-')
throw new DefaultParserException ("'-' expected", null);
int cnt;
int lst;
while (true) {
readTo ('-', buf);
if (readChar () == -1)
throw new DefaultParserException (UNEXPECTED_EOF, null);
cnt = 0;
do {
lst = readChar ();
cnt++; // adds one more, but first is not cnted
}
while (lst == '-');
if (lst == '>' && cnt >= 2) break;
while (cnt-- > 0)
buf.append ('-');
buf.append ((char) lst);
}
while (cnt-- > 2)
buf.append ('-');
return new ParseEvent (Xml.COMMENT, buf.toString ());
}
/* precondition: <! consumed */
ParseEvent parseDoctype () throws IOException {
StringBuffer buf = new StringBuffer ();
int nesting = 1;
while (true) {
int i = readChar ();
switch (i) {
case -1:
throw new DefaultParserException (UNEXPECTED_EOF, null);
case '<':
nesting++;
break;
case '>':
if ((--nesting) == 0)
return new ParseEvent (Xml.DOCTYPE, buf.toString ());
break;
}
buf.append ((char) i);
}
}
ParseEvent parseCData () throws IOException {
StringBuffer buf = readTo ('[', new StringBuffer ());
if (!buf.toString ().equals ("CDATA"))
throw new DefaultParserException ("Invalid CDATA start!", null);
buf.setLength (0);
readChar (); // skip '['
int c0 = readChar ();
int c1 = readChar ();
while (true) {
int c2 = readChar ();
if (c2 == -1)
throw new DefaultParserException (UNEXPECTED_EOF, null);
if (c0 == ']' && c1 == ']' && c2 == '>')
break;
buf.append ((char) c0);
c0 = c1;
c1 = c2;
}
return new ParseEvent (Xml.TEXT, buf.toString ());
}
/* precondition: </ consumed */
ParseEvent parseEndTag () throws IOException {
skipWhitespace ();
closePending = readName ();
skipWhitespace ();
if (readChar () != '>')
throw new DefaultParserException ("'>' expected", null);
return checkEndTag ();
}
public ParseEvent checkEndTag () throws IOException {
int last = qNames.size ();
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -