7

Java 的 XML 解析器似乎认为我的 XML 文档在根元素之后的格式不正确。但是我已经用几种工具对其进行了验证,但他们都不同意。这可能是我的代码中的错误,而不是文档本身中的错误。我真的很感激你们能提供给我的任何帮助。

这是我的Java方法:

private void loadFromXMLFile(File f) throws ParserConfigurationException, IOException, SAXException {
    File file = f;
    DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
    DocumentBuilder db;
    Document doc = null;
    db = dbf.newDocumentBuilder();
    doc = db.parse(file);
    doc.getDocumentElement().normalize();
    String desc = "";
    String due = "";
    String comment = "";
    NodeList tasksList = doc.getElementsByTagName("task");
    for (int i = 0; i  tasksList.getLength(); i++) {
        NodeList attributes = tasksList.item(i).getChildNodes();
        for (int j = 0; i < attributes.getLength(); j++) {
        Node attribute = attributes.item(i);
        if (attribute.getNodeName() == "description") {
            desc = attribute.getTextContent();
        }
        if (attribute.getNodeName() == "due") {
            due = attribute.getTextContent();
        }
        if (attribute.getNodeName() == "comment") {
            comment = attribute.getTextContent();
        }
        tasks.add(new Task(desc, due, comment));
        }
        desc = "";
        due = "";
        comment = "";
    }
}

以下是我尝试加载的 XML 文件:

<?xml version="1.0"?>  
<tasklist>  
    <task>  
        <description>Task 1</description>  
        <due>Due date 1</due>  
        <comment>Comment 1</comment>  
        <completed>false</completed>  
    </task>  
    <task>  
        <description>Task 2</description>  
        <due>Due date 2</due>  
        <comment>Comment 2</comment>  
        <completed>false</completed>  
    </task>  
    <task>  
        <description>Task 3</description>  
        <due>Due date 3</due>  
        <comment>Comment 3</comment>  
        <completed>true</completed>  
    </task>  
</tasklist>

这是java为我抛出的错误消息:

run:
[Fatal Error] tasks.xml:28:3: The markup in the document following the root element must be well-formed.
May 17, 2010 6:07:02 PM todolist.TodoListGUI <init>
SEVERE: null
org.xml.sax.SAXParseException: The markup in the document following the root element must be well-formed.
        at com.sun.org.apache.xerces.internal.parsers.DOMParser.parse(DOMParser.java:239)
        at com.sun.org.apache.xerces.internal.jaxp.DocumentBuilderImpl.parse(DocumentBuilderImpl.java:283)
        at javax.xml.parsers.DocumentBuilder.parse(DocumentBuilder.java:208)
        at todolist.TodoListGUI.loadFromXMLFile(TodoListGUI.java:199)
        at todolist.TodoListGUI.<init>(TodoListGUI.java:42)
        at todolist.Main.main(Main.java:25)
BUILD SUCCESSFUL (total time: 19 seconds)

供参考 TodoListGUI.java:199 是

doc = db.parse(file);

如果上下文对这里的任何人都有帮助,我正在尝试编写一个简单的 GUI 应用程序来管理一个 todo 列表,该列表可以读取和写入定义任务的 XML 文件。

4

6 回答 6

12

org.xml.sax.SAXParseException:文档中根元素之后的标记必须格式正确。

这一特殊异常表明 XML 文档中有多个根元素。换句话说,<tasklist>不是唯一的根元素。以您的 XML 文档为例,考虑一个没有<tasklist>元素而根中有三个<task>元素的文档。这会导致这种异常。

由于您发布的 XML 文件看起来不错,因此问题出在其他地方。看起来它没有解析您期望它正在解析的 XML 文件。为了快速调试,将以下内容添加到您的方法顶部:

System.out.println(f.getAbsolutePath());

在磁盘文件系统中找到该文件并进行验证。

于 2010-05-18T00:29:05.490 回答
4

我认为实际文件可能有问题。当我复制您的代码但使用 XML 作为解析器的字符串输入时,它可以正常工作(在修复了几个问题之后 -attributes.item(i)应该是attributes.item(j)并且您需要在何时跳出循环attribute == null)。

在尝试重现您的错误时,如果我添加另一个<tasklist></tasklist>元素,我会收到相同的消息。这是因为 XML 不再具有单个根元素(任务列表)。这是你看到的问题吗?中的 XML 是否tasks.xml有单个根元素?

于 2010-05-17T23:43:42.960 回答
1

尝试将您的 XML 声明更改为:

<?xml version="1.0" encoding="UTF-8" ?>
于 2010-05-17T22:14:24.683 回答
0

另一个物有所值,这是我将您的 xml 保存到一个名为test.xml并通过xmllint运行它的文件时得到的。

[jhr@Macintosh] [~]
xmllint test.xml
<?xml version="1.0"?>
<tasklist>  
    <task>  
        <description>Task 1</description>  
        <due>Due date 1</due>  
        <comment>Comment 1</comment>  
        <completed>false</completed>  
    </task>  
    <task>  
        <description>Task 2</description>  
        <due>Due date 2</due>  
        <comment>Comment 2</comment>  
        <completed>false</completed>  
    </task>  
    <task>  
        <description>Task 3</description>  
        <due>Due date 3</due>  
        <comment>Comment 3</comment>  
        <completed>true</completed>  
    </task>  
</tasklist>

似乎很好。很可能您有一些在实际文件中看不到的杂散字符。尝试在将显示不可打印字符的编辑器中查看实际文件,就像其他人建议的那样,如果这不是英文 UTF-8 机器,您可能有一些 Unicode 字符,您看不到解析器。那或者您没有加载您认为的文件。单步调试并在文件输入解析器之前查看文件的实际内容。

于 2010-05-18T00:29:40.543 回答
0

值得一提的是,Scala REPL 成功解析了您的标记。

scala> val tree = <tasklist>
 | <task>
 | <description>Task 1</description>
 | <due>Due date 1</due>
 | <comment>Comment 1</comment>
 | <completed>false</completed>
 | </task>
 | <task>
 | <description>Task 2</description>
 | <due>Due date 2</due>
 | <comment>Comment 2</comment>
 | <completed>false</completed>
 | </task>
 | <task>
 | <description>Task 3</description>
 | <due>Due date 3</due>
 | <comment>Comment 3</comment>
 | <completed>true</completed>
 | </task>
 | </tasklist>
tree: scala.xml.Elem = 
<tasklist>
<task>
<description>Task 1</description>
<due>Due date 1</due>
<comment>Comment 1</comment>
<completed>false</completed>
</task>
<task>
<description>Task 2</description>
<due>Due date 2</due>
<comment>Comment 2</comment>
<completed>false</completed>
</task>
<task>
<description>Task 3</description>
<due>Due date 3</due>
<comment>Comment 3</comment>
<completed>true</completed>
</task>
</tasklist>
于 2010-05-18T00:03:53.757 回答
0

您确定这是该文件中的所有内容吗?该错误抱怨在当前根之后有更多标记。所以后面肯定有别的东西</tasklist>

有时,此错误可能是由不可打印的字符引起的。如果您没有看到任何内容,请对文件执行 hexdump。

于 2010-05-18T01:03:05.880 回答