簡體   English   中英

如何解析具有相同標簽名稱的嵌套 xml 標簽

[英]How to parse nested xml tags with the same tag name

我有未指定數量的嵌套類別,其中包含項目:

<categories>
    <category>abc
        <category>cde
            <item>someid</item>
            <item>someid</item>
            <item>someid</item>
            <item>someid</item>
        </category>
    </category>
<category>xyz
   <category>zwd
       <category>hgw
           <item>someid</item>
...

結果應該是嵌套最深的類別(cde 或 hgw)中的項目列表。 棘手的是,類別的嵌套可以有兩個以上級別,我想為子類別保存每個父類別。

我已經用 Jackson XmlMapper 和 ObjectMapper 做了一些 xml 解析,但是這個用例似乎遙不可及。 所以我用 javax xml 解析器嘗試了它但放棄了,因為代碼看起來很糟糕而且幾乎不可讀。

知道如何以更優雅的方式解決這個問題嗎?

如果任務是從 xml 中快速提取一些值,那么我會使用 jsoup。 Jsoup實際上是一個 html 解析器,但也能夠解析 xml。 我不確定 jsoup 是否還可以驗證 xml 模式並處理命名空間和……這在其他解析器中是可能的。 但是讀取一些值 jsoup 通常對我來說就足夠了。 如果您想查看Jsoup 食譜選擇器語法

馬文:

<!-- https://mvnrepository.com/artifact/org.jsoup/jsoup -->
<dependency>
    <groupId>org.jsoup</groupId>
    <artifactId>jsoup</artifactId>
    <version>1.13.1</version>
</dependency>

使用 jsoup 您的代碼可能如下所示:

import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.parser.Parser;
import org.jsoup.select.Elements;

public class Example {


    public static void main(String[] args) {
        String xml = "<categories>\n"
                + "    <category>abc\n"
                + "        <category>cde\n"
                + "            <item>someid_1</item>\n"
                + "            <item>someid_2</item>\n"
                + "            <item>someid_3</item>\n"
                + "            <item>someid_4</item>\n"
                + "        </category>\n"
                + "    </category>\n"
                + "    <category>xyz\n"
                + "       <category>zwd\n"
                + "          <category>hgw\n"
                + "             <item>someid_5</item>\n"
                + "          </category>\n"
                + "       </category>\n"
                + "    </category>\n"
                + " </categories>";

        Document doc = Jsoup.parse(xml, "", Parser.xmlParser());

        //if you are interested in Items only
        Elements items = doc.select("category > item");
        items.forEach(i -> {
            System.out.println("Parent text: " +i.parent().ownText());
            System.out.println("Item text: "+ i.text());
            System.out.println();
        });


        //if you are interested in categories having at least one direct item element
        Elements categories = doc.select("category:has(> item)");
        categories.forEach(c -> {
            System.out.println(c.ownText());
            Elements children = c.children();
            children.forEach(ch -> {
                System.out.println(ch.text());
            });
            System.out.println();
        });
    }

}

輸出:

Parent text: cde
Item text: someid_1

Parent text: cde
Item text: someid_2

Parent text: cde
Item text: someid_3

Parent text: cde
Item text: someid_4

Parent text: hgw
Item text: someid_5

cde
someid_1
someid_2
someid_3
someid_4

hgw
someid_5

暫無
暫無

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

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