Jsoup - 提取文本

Posted

技术标签:

【中文标题】Jsoup - 提取文本【英文标题】:Jsoup - extracting text 【发布时间】:2012-04-28 00:05:30 【问题描述】:

我需要从这样的节点中提取文本:

<div>
    Some text <b>with tags</b> might go here.
    <p>Also there are paragraphs</p>
    More text can go without paragraphs<br/>
</div>

我需要构建:

Some text <b>with tags</b> might go here.
Also there are paragraphs
More text can go without paragraphs

Element.text 只返回 div 的所有内容。 Element.ownText - 不在子元素中的所有内容。两者都是错误的。遍历children 会忽略文本节点。

是否有办法迭代元素的内容以接收文本节点。例如

文本节点 - 一些文本 节点 - 带有标签 文本节点 - 可能在此处。 节点

- 还有段落

文本节点 - 更多文本可以不带段落 节点 -

【问题讨论】:

【参考方案1】:

您可以为此目的使用 TextNode:

List<TextNode> bodyTextNode = doc.getElementById("content").textNodes();
    String html = "";
    for(TextNode txNode:bodyTextNode)
        html+=txNode.text();
    

【讨论】:

【参考方案2】:

假设您只想要文本(无标签),我的解决方案如下。 输出是: 一些带有标签的文本可能会放在这里。还有段落。更多文本可以不带段落

public static void main(String[] args) throws IOException 
    String str = 
                "<div>"  
            +   "    Some text <b>with tags</b> might go here."
            +   "    <p>Also there are paragraphs.</p>"
            +   "    More text can go without paragraphs<br/>" 
            +   "</div>";

    Document doc = Jsoup.parse(str);
    Element div = doc.select("div").first();
    StringBuilder builder = new StringBuilder();
    stripTags(builder, div.childNodes());
    System.out.println("Text without tags: " + builder.toString());


/**
 * Strip tags from a List of type <code>Node</code>
 * @param builder StringBuilder : input and output
 * @param nodesList List of type <code>Node</code>
 */
public static void stripTags (StringBuilder builder, List<Node> nodesList) 

    for (Node node : nodesList) 
        String nodeName  = node.nodeName();

        if (nodeName.equalsIgnoreCase("#text")) 
            builder.append(node.toString());
         else 
            // recurse
            stripTags(builder, node.childNodes());
        
    

【讨论】:

【参考方案3】:
for (Element el : doc.select("body").select("*")) 

        for (TextNode node : el.textNodes()) 

                    node.text() ));

        

    

【讨论】:

我猜你在循环中缺少一个 system.out.println,但这是递归提取所有文本节点的示例。【参考方案4】:

Element.children() 返回一个 Elements 对象 - Element 对象的列表。查看父类Node,您会看到让您可以访问任意节点的方法,而不仅仅是元素,例如Node.childNodes()。

public static void main(String[] args) throws IOException 
    String str = "<div>" +
            "    Some text <b>with tags</b> might go here." +
            "    <p>Also there are paragraphs</p>" +
            "    More text can go without paragraphs<br/>" +
            "</div>";

    Document doc = Jsoup.parse(str);
    Element div = doc.select("div").first();
    int i = 0;

    for (Node node : div.childNodes()) 
        i++;
        System.out.println(String.format("%d %s %s",
                i,
                node.getClass().getSimpleName(),
                node.toString()));
    

结果:

1 个文本节点 一些文字 2 元素带标签 3 TextNode 可能会放在这里。 4元素

还有段落

5 TextNode 更多文字可以不用段落 6元素

【讨论】:

以上是关于Jsoup - 提取文本的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 Jsoup 提取单独的文本节点?

Jsoup代码示例解析网页+提取文本

如何在java中提取网页文本内容? [关闭]

使用 jsoup 提取信息

jsoup 提取 html 中的所有链接图片和媒体

Jsoup:在无 CSS 的 HTML 中提取两个块之间的所有 HTML