使用Jsoup,我希望能够将每个html标记中存在的文本依次添加到List<String>
中。
这在python中使用BeautifulSoup4相当容易,但我在Java中却很难。
BeautifulSoup代码:
from bs4 import BeautifulSoup
from bs4.element import Comment
import urllib.request
def tag_visible(element):
if element.parent.name in ['style', 'script', 'head', 'title', 'meta', '[document]']:
return False
if isinstance(element, Comment):
return False
return True
def text_from_html(body):
soup = BeautifulSoup(body, 'html.parser')
texts = soup.findAll(text=True)
visible_texts = filter(tag_visible, texts)
text_list =[]
for t in visible_texts:
text_list.append(t.strip())
return list(filter(None, text_list))
html = urllib.request.urlopen('https://someURL.com/something').read()
print(text_from_html(html))
此代码将打印["text1", "text2", "text3",...]
我最初的尝试是遵循Jsoup文档进行文本转换。
Jsoup代码尝试1:
Document doc = Jsoup.connect('https://someURL.com/something')
.userAgent("Bot")
.get();
Elements divElements = doc.select("*")
List<String> texts = divElements.eachText();
System.out.println(texts);
最终发生的是文本["text1 text2 text3","text2 text3", "text3",...]
的重复
我的假设是Jsoup遍历每个Element并打印出Element中的每个文本,包括每个子节点中存在的文本。然后转到子节点并打印出剩余的文本,依此类推。
我已经看到很多人通过cssQuery指定标签/属性来绕过此问题,但是我的项目要求对任何可抓取的网站执行此操作。
任何建议都值得赞赏。
答案 0 :(得分:0)
您的假设是正确的-但BeautifulSoup可能也会这样做。 text=True
中只有findAll(text=True)
将结果限制为纯文本节点。要在JSoup中具有等效功能,请使用以下选择器:
Elements divElements = doc.select(":matchText");