为啥我会获得额外的文本节点作为根节点的子节点?

Posted

技术标签:

【中文标题】为啥我会获得额外的文本节点作为根节点的子节点?【英文标题】:Why am I getting extra text nodes as child nodes of root node?为什么我会获得额外的文本节点作为根节点的子节点? 【发布时间】:2013-12-14 02:44:52 【问题描述】:

我想打印根节点的子元素。这是我的 XML 文件。

<?xml version="1.0"?>
<!-- Comment-->
<company>
   <staff id="1001">
       <firstname>yong</firstname>
       <lastname>mook kim</lastname>
       <nickname>mkyong</nickname>
       <salary>100000</salary>
   </staff>
   <staff id="2001">
       <firstname>low</firstname>
       <lastname>yin fong</lastname>
       <nickname>fong fong</nickname>
       <salary>200000</salary>
   </staff>
</company>

根据我的理解,根节点是'company',它的子节点必须是'staff'和'staff'(因为'staff'节点有2次)。但是当我试图通过我的 java 代码获取它们时,我得到了 5 个子节点。 3 个额外的文本节点来自哪里?

Java 代码:

package com.training.xml;

import java.io.File;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;

public class ReadingXML 

public static void main(String[] args) 
    try 

        File file = new File("D:\\TestFile.xml");

        DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
        DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
        Document doc = dBuilder.parse(file);
        doc.getDocumentElement().normalize();

        System.out.println("root element: " + doc.getDocumentElement().getNodeName());

        Node rootNode = doc.getDocumentElement(); 
        System.out.println("root: " + rootNode.getNodeName());

        NodeList nList = rootNode.getChildNodes(); 

        for(int i = 0; i < nList.getLength(); i++) 
            System.out.println("node name: " + nList.item(i).getNodeName() );
                   
     catch(Exception e) 
        e.printStackTrace();
    


输出:

root element: company
root: company
node name: #text
node name: staff
node name: #text
node name: staff
node name: #text

为什么三个文本节点会过来?

【问题讨论】:

【参考方案1】:

为什么三个文本节点会过来?

它们是子元素之间的空白。如果你只想要子元素,你应该忽略其他类型的节点:

for (int i = 0;i < nList.getLength(); i++) 
    Node node = nList.item(i);
    if (node.getNodeType() == Node.ELEMENT_NODE) 
        System.out.println("node name: " + node.getNodeName());
    

或者您可以将文档更改为没有空格。

或者您可以使用不同的 XML API,它允许您轻松地请求元素。 (DOM API 在很多方面都很痛苦。)

如果只想忽略元素内容空格,可以使用Text.isElementContentWhitespace

【讨论】:

谢谢!它起作用了:) 还有一件事,它将换行符作为文本节点。换行符是空格吗?有没有办法只获取子元素而不是文本节点作为输出,因为我必须将换行符放在我的 XML 文件中,并且它将换行符显示为文本节点。 @VikasMangal:是的,换行符是空格。我的答案包括只查看元素的代码。 我在 javascript 中遇到了同样的问题,这个解决方案也适用于它:D 我对 oracle 的 xmlparserverV2 .jar 有同样的问题。解决空白问题后,它也对我有用。 parser.setPreserveWhitespace(false); 我发现一个选项似乎可以设置解析器忽略空格,但是,在我的测试之后它似乎不起作用:dbFactory.setNamespaceAware(true); dbFactory.setIgnoringElementContentWhitespace(true); 有什么想法吗?

以上是关于为啥我会获得额外的文本节点作为根节点的子节点?的主要内容,如果未能解决你的问题,请参考以下文章

如何反序列化xml文件的子节点

POJ2117 Electricity

ASP中关于TreeView控件的问题,怎样展开、收缩所有子节点?

easyUI tree jQuery

并查集-解决区间和纠错问题 hdu-3038

域驱动设计:如何访问聚合根的子节点