【问题标题】:How to select all elements containing actual text using Jsoup?如何使用 Jsoup 选择包含实际文本的所有元素?
【发布时间】:2023-03-22 21:52:01
【问题描述】:

Jsoup 将每个文本保存为一个文本节点,包括元素之间的 \r\n 内容。我想选择页面上的所有真实文本并选择其父级以删除该父级中的所有文本。

我目前有这个:

document.select("*:containsOwn(\n)").remove();
    for(int i = 1; i < document.size(); i++){
        if(document.get(i).hasText()){
            List<Element> removableElements = document.get(i).parent().getAllElements();
            for (Element e1 : removableElements) {
                e1.remove();
            }
        }

    }

它不会删除所有包含 \n 的文本节点,因此它会尝试删除正文,因为这是第一个包含文本节点的元素。

我只想选择所有带有文本的元素并执行 element.parent().children().remove();

document.select("*:contains( )"); 

也没有按照我想要的方式工作。

这个问题与this问题有关,但不一样。

编辑:

输入:

<div>
    <ul>
        <li>some menu item</li>
        <li>some menu item</li>
        <li>some menu item</li>
    </ul>
</div>
<div>
    <h3>Tile of some text</h3>
    <p></p>
    <p>some text</p>
    <ul>
        <li>some other text</li>
        <li>some other text</li>
        <li>some other text</li>
    </ul>
</div>

输出:

<li>some menu item</li>
<li>some menu item</li>
<li>some menu item</li>
<h3>Tile of some text</h3>
<p></p>
<p>some text</p>
<li>some other text</li>
<li>some other text</li>
<li>some other text</li>

【问题讨论】:

  • 你能添加一个输入和预期输出的例子吗?
  • &lt;p&gt;&lt;/p&gt; 在输出中与您的规则“包含实际文本”相矛盾。这意味着您必须允许特殊情况“空 p 标签”,因为它可能只是更复杂网站的示例,您最终会遇到很多特殊情况,因为有很多文本级元素stackoverflow.com/a/7130146/1661938您的相关/链接问题中存在类似问题:您想要一个通用解决方案,但提出一个特殊情况。也许你应该重新考虑你的方法或者更详细地描述你的目标(例如:菜单总是一样的?)。

标签: java html jsoup


【解决方案1】:

作为预期输出的一部分的空 p 标签的特殊情况(即使它与“包含实际文本”的规则相矛盾)需要特殊的解析。对于更复杂的文档/在输出中允许更多空 text-level elements 的解决方案,将需要额外的 if 语句来处理这些元素(首先比较 if 语句):

String htmlString = "<div><ul><li>some menu item</li><li>some menu item</li><li>some menu item</li></ul></div><div><h3>Tile of some text</h3><p></p><p>some text</p><ul><li>some other text</li><li>some other text</li><li>some other text</li></ul></div>";
Document doc = Jsoup.parse(htmlString);

for (Element element : doc.getAllElements()) {
    if(element.nodeName().equals("p") && element.childNodes().size()==0){
        System.out.println(element.toString());
    }
    else if(element.childNodes().size()>0 && element.childNode(0).nodeName().equals("#text")){
        System.out.println(element.toString());
    }
}

输出:

<li>some menu item</li>
<li>some menu item</li>
<li>some menu item</li>
<h3>Tile of some text</h3>
<p></p>
<p>some text</p>
<li>some other text</li>
<li>some other text</li>
<li>some other text</li>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-05-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-10-25
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多