簡體   English   中英

解析具有相同名稱的嵌套XML標簽

[英]Parse Nested XML tags with the same name

讓我們看一個簡單的XML文檔:

  <x>
    <e>
        <e>
            <e>Whatever 1</e>
        </e>
    </e>
    <e>
        <e>
            <e>Whatever 2</e>
        </e>
    </e>
    <e>
        <e>
            <e>Whatever 3</e>
        </e>
    </e>
  </x> 

使用標准的org.w3c.dom,我可以通過這樣做來獲取X中的節點。

NodeList fullnodelist = doc.getElementsByTagName("x");

但是,如果我想返回下一組“ e”,則嘗試使用..

Element element = (Element) fullnodelist.item(0);
NodeList nodes = pelement.getElementsByTagName("e");

期望它返回“ 3”個節點(因為有3套“ e”),但是,它返回“ 9”-因為它會相應地獲得所有帶有“ e”的條目。

在上述情況下,這會很好,因為我可能可以遍歷並找到想要的東西。 我遇到的問題是,當XML文件如下所示時:

  <x>
    <e>
      <pattern>whatever</pattern>
      <blanks>
        <e>Something Else</e>
      </blanks>
    </e>
    <e>
      <pattern>whatever</pattern>
      <blanks>
        <e>Something Else</e>
      </blanks>
    </e>
  </x>

當我請求“ e”值時,它返回4,而不是(我期望的)2。

我只是不了解DOM解析的工作原理嗎? 通常,過去我使用自己的XML文檔,所以我永遠都不會這樣命名項目,但是不幸的是,這不是我的XML文件,因此我別無選擇。

我以為我會寫一個“向下鑽取”節點的循環,以便可以將每個節點組合在一起...

public static NodeList getNodeList(Element pelement, String find)
    {
        String[] nodesfind = Utilities.Split(find, "/");
        NodeList nodeList = null;

        for (int i = 0 ; i <= nodesfind.length - 1; i++ )
        {
            nodeList = pelement.getElementsByTagName( nodesfind[i] );
            pelement = (Element)nodeList.item(i);
        }

        // value of the nod we are looking for
        return nodeList;
    }

..因此,如果將“ s / e”傳遞給函數,它將返回我要查找的2個節點(或元素,也許我使用的術語不正確?)。 而是返回該節點內的所有“ e”節點。

我為此使用了J2SE,因此選項相當有限。 我不能使用任何第三方XML解析器。

無論如何,如果有人仍在我身邊並且有建議,將不勝感激。

如果您是手動遍歷Xml,請嘗試使用一個變量,該變量在遇到每個“ e”標簽時遞增,然后在離開時遞減。

如果源遵循您上面給出的示例,則可以在執行操作之前使用簡單的if語句確保計數器等於2(假設計數器從0開始)。

我可能會稍微誤解了您的確切問題,但是希望對您有所幫助。

比計數器更好的解決方案是檢查每個返回的節點,以查看它們是否具有正確的父節點。

getChildNodes()返回所有子getChildNodes()返回所有后代 (即完整的子樹)。

  Element element = doc.getDocumentElement();
  NodeList nodeList = element.getChildNodes();
  for (int i = 0; i < nodeList.getLength(); i++ ) {
    if (nodeList.item(i).getNodeType() == Node.ELEMENT_NODE && nodeList.item(i).getParentNode().isSameNode(element)) {
      Element childElement = (Element) nodeList.item(i);
      if (childElement.getTagName().equals("someTagName")) {
        handleSomeTag(childElement);
      } else if (childElement.getTagName().equals("someOtherTagName")) {
        handleSomeOtherTag(childElement);
      }
    }
  }

getElementsByTagName()返回具有該標記名的所有子代 ,而且還返回具有該標記名的所有后代 (即,在整個子樹中具有該名稱的所有標記)。

  Element element = doc.getDocumentElement();
  NodeList nodeList = element.getElementsByTagName("someTag");
  for (int i = 0; i < nodeList.getLength(); i++ ) {
    if (nodeList.item(i).getNodeType() == Node.ELEMENT_NODE && nodeList.item(i).getParentNode().isSameNode(element)) {
      Element childElement = (Element) nodeList.item(i);
      handleSomeTag(childElement);
    }
  }
  nodeList = element.getElementsByTagName("someOtherTag");
  for (int i = 0; i < nodeList.getLength(); i++ ) {
    if (nodeList.item(i).getNodeType() == Node.ELEMENT_NODE && nodeList.item(i).getParentNode().isSameNode(element)) {
      Element childElement = (Element) nodeList.item(i);
      handleSomeOtherTag(childElement);
    }
  }

您需要了解XPath。 Java 1.5中有一個XPathFactory,您可以創建一個XPath來命名所需的特定“ e”。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM