Java识别和处理HTML标签内容的常用方法
作者:白大锅
这篇文章总结了识别和处理HTML的几种方法:推荐使用Jsoup处理复杂结构,因其功能强大且API友好;避免正则表达式和XML解析器处理嵌套标签;需清理用户输入中的潜在安全风险,并注意字符编码问题,需要的朋友可以参考下
1. 使用正则表达式(简单场景)
适用于简单的 HTML 标签识别和提取:
import java.util.regex.Matcher; import java.util.regex.Pattern; public class HtmlTagExtractor { public static void main(String[] args) { String html = "<div><p>Hello <b>World</b></p><a href='example.com'>Link</a></div>"; // 匹配所有标签 Pattern tagPattern = Pattern.compile("<[^>]+>"); Matcher tagMatcher = tagPattern.matcher(html); System.out.println("所有HTML标签:"); while (tagMatcher.find()) { System.out.println(tagMatcher.group()); } // 匹配特定标签(如<a>标签) Pattern aTagPattern = Pattern.compile("<a\\b[^>]*>(.*?)</a>"); Matcher aTagMatcher = aTagPattern.matcher(html); System.out.println("\n所有<a>标签:"); while (aTagMatcher.find()) { System.out.println("完整标签: " + aTagMatcher.group(0)); System.out.println("标签内容: " + aTagMatcher.group(1)); } // 匹配标签属性 Pattern attrPattern = Pattern.compile("\\b(href|src)=['\"]([^'\"]*)['\"]"); Matcher attrMatcher = attrPattern.matcher(html); System.out.println("\n所有href/src属性:"); while (attrMatcher.find()) { System.out.println(attrMatcher.group(1) + " = " + attrMatcher.group(2)); } } }
注意:正则表达式不适合处理复杂的、嵌套的 HTML 结构。
2. 使用 Jsoup(推荐)
Jsoup 是一个强大的 Java HTML 解析库:
import org.jsoup.Jsoup; import org.jsoup.nodes.Document; import org.jsoup.nodes.Element; import org.jsoup.select.Elements; public class JsoupExample { public static void main(String[] args) { String html = "<html><head><title>Sample</title></head>" + "<body><div id='content'><p class='text'>First paragraph</p>" + "<p>Second <b>paragraph</b></p><a href='example.com'>Link</a></div></body></html>"; // 解析HTML Document doc = Jsoup.parse(html); // 获取标题 System.out.println("标题: " + doc.title()); // 获取所有段落 Elements paragraphs = doc.select("p"); System.out.println("\n所有段落:"); for (Element p : paragraphs) { System.out.println(p.text()); } // 获取特定ID的元素 Element contentDiv = doc.getElementById("content"); System.out.println("\nID为content的div:"); System.out.println(contentDiv.html()); // 获取特定class的元素 Elements textElements = doc.getElementsByClass("text"); System.out.println("\nclass为text的元素:"); for (Element el : textElements) { System.out.println(el.text()); } // 获取所有链接 Elements links = doc.select("a[href]"); System.out.println("\n所有链接:"); for (Element link : links) { System.out.println("文本: " + link.text() + ", 链接: " + link.attr("href")); } // 获取元素的父级和子级 Element firstP = paragraphs.first(); System.out.println("\n第一个段落的父元素: " + firstP.parent().tagName()); System.out.println("第一个段落的子元素数量: " + firstP.children().size()); } }
3. 使用 JDK 内置的 XML 解析器(适用于 XHTML)
对于格式良好的 XHTML,可以使用 JDK 内置的 XML 解析器:
import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import org.w3c.dom.Document; import org.w3c.dom.NodeList; public class XmlParserExample { public static void main(String[] args) throws Exception { String xhtml = "<html><body><p>Paragraph 1</p><p>Paragraph 2</p></body></html>"; DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder = factory.newDocumentBuilder(); Document doc = builder.parse(new InputSource(new StringReader(xhtml))); // 获取所有段落 NodeList paragraphs = doc.getElementsByTagName("p"); System.out.println("找到 " + paragraphs.getLength() + " 个段落:"); for (int i = 0; i < paragraphs.getLength(); i++) { System.out.println(paragraphs.item(i).getTextContent()); } } }
4. 使用 HTMLCleaner
HTMLCleaner 是另一个轻量级的 HTML 解析库:
import org.htmlcleaner.HtmlCleaner; import org.htmlcleaner.TagNode; public class HtmlCleanerExample { public static void main(String[] args) throws Exception { String html = "<html><body><div><p>Hello</p><p>World</p></div></body></html>"; HtmlCleaner cleaner = new HtmlCleaner(); TagNode rootNode = cleaner.clean(html); // 获取所有段落 TagNode[] paragraphs = rootNode.getElementsByName("p", true); System.out.println("找到 " + paragraphs.length + " 个段落:"); for (TagNode p : paragraphs) { System.out.println(p.getText().toString()); } } }
5. 处理 HTML 文本(去除标签)
如果只需要提取文本内容而不需要标签结构:
import org.jsoup.Jsoup; public class HtmlTextExtractor { public static void main(String[] args) { String html = "<div><p>Hello <b>World</b></p><a href='example.com'>Link</a></div>"; // 使用Jsoup提取文本 String text = Jsoup.parse(html).text(); System.out.println("纯文本内容:\n" + text); // 简单正则方法去除标签(不推荐用于复杂HTML) String textOnly = html.replaceAll("<[^>]+>", ""); System.out.println("\n简单去除标签后的文本:\n" + textOnly); } }
最佳实践建议
- 推荐使用 Jsoup:它功能强大、API友好,适合大多数HTML处理场景
- 避免使用正则处理复杂HTML:正则表达式难以正确处理嵌套标签和格式不规范的HTML
- 注意HTML清理:当处理用户输入的HTML时,应该清理潜在的恶意内容
- 考虑性能:对于大量HTML处理,Jsoup的性能通常足够好
- 处理编码问题:确保正确处理HTML文档的字符编码
安全注意事项
当处理用户提供的HTML内容时,务必考虑安全风险:
import org.jsoup.Jsoup; import org.jsoup.safety.Safelist; public class HtmlSanitizer { public static void main(String[] args) { String unsafeHtml = "<div onclick='alert(\"xss\")'>Hello<script>alert('xss')</script><a href='javascript:alert(1)'>Link</a></div>"; // 基本清理,只允许文本 String safeText = Jsoup.clean(unsafeHtml, Safelist.none()); System.out.println("仅文本:\n" + safeText); // 允许基本格式和安全的链接 String basicHtml = Jsoup.clean(unsafeHtml, Safelist.basic()); System.out.println("\n基本HTML:\n" + basicHtml); // 自定义白名单 Safelist customList = Safelist.basic() .addTags("div", "span") .addAttributes("div", "class"); String customClean = Jsoup.clean(unsafeHtml, customList); System.out.println("\n自定义清理:\n" + customClean); } }
到此这篇关于Java识别和处理HTML标签内容的常用方法的文章就介绍到这了,更多相关Java识别和处理HTML内容内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!