1、简介

HTMLParser 也是一款非常高效的 HTML 解析器,其支持 CSS 选择器提取 HTML中的节点。HTMLParser 的版本已不再更新,但并不影响其使用。

2、jar包下载

<dependency> 
	<groupId>org.htmlparser</groupId> 	
	<artifactId>htmlparser</artifactId> 
	<version>2.1</version>
</dependency>

3、相关方法

HTMLParser 的核心类是 org.htmlparser.Parser,其主要功能是实例化 Parser。下表列举了该类中常用的构造方法。

方法说明
Parser()无参数构造
Parser(Lexer lexer)通过 Lexer 构造 Parser,在案例程序中会使用到
Parser(String resource)给定一个 URL 或文件资源,构造 Parser
Parser(URLConnection connection)使用 URLConnection 构造 Parser

上表中的几种构造方法能够创建 Parser 对象。在 Parser 对象创建完成后,需要 执行过滤(Filter)任务,即获取包含解析内容的一系列节点,下表所示为执行过滤 任务常用的过滤器。

方法说明
TagNameFilter (String name)根据标签名称进行过滤
NodeClassFilter (Class cls)根据类名进行过滤
HasAttributeFilter (String attribute)匹配出包含指定属性的节点
HasAttributeFilter (String attribute, String value)匹配出包含指定属性与属性值的节点
AndFilter (NodeFilter left, NodeFilter right)结合几种过滤条件的“与”过滤器
OrFilter (NodeFilter left, NodeFilter right)结合几种过滤条件的“或”过滤器
StringFilter (String pattern)根据模式对象进行过滤
RegexFilter (String pattern)根据正则表达式进行过滤
LinkStringFilter (String pattern)判断链接中是否包含某个特定的字符串,可以用来过滤出指向某个特定网站的链接
CssSelectorNodeFilter (String selector)根据 CSS 选择器获取节点(最常用)

完成过滤(Filter)操作之后,便要对具体的节点进行操作,常用的方法如下表所示。

方法说明
NodeList getChildren()获取子节点列表
Node getParent()获取父节点
Node getFirstChild()获取第一个子节点
Node getLastChild()获取最后一个子节点
Node getPreviousSibling()获取上一个兄弟节点
Node getNextSibling()获取下一个兄弟节点
String getText()获取节点的文本数据(包括标签名称、属性及属性值以及标签内的数据)
String toPlainTextString()获取节点标签内的数据,注意和 getText()的区别
String toHtml()返回节点对应的 HTML 片段
Page getPage()获取节点对应的 Page 对象
int getStartPosition()获取节点在 HTML 页面中的起始位置
int getEndPosition()获取节点在 HTML 页面中的结束位置

4、案例

4.1、案例一

首 先,使用 Jsoup 获取指定 URL 对应的 HTML 字符串,接着使用 Parser(Lexer lexer)构 造方法创建 Parser 对象,然后结合过滤器以及操作节点的相关方法提取 HTML 中的所 有链接(即 href 的属性值和链接对应的标题)。

public class HTMLParserTest1 {
    public static void main(String[] args) throws IOException, ParserException {
        Document doc = Jsoup.connect("https://www.runoob.com")
                .timeout(5000).get();
        String html = doc.html();
        //使用lexer构造
        Lexer lexer = new Lexer(html);
        Parser parser = new Parser(lexer);
        //过滤页面中的链接标签
        NodeFilter filter = new NodeClassFilter(LinkTag.class);
        //获取匹配到的节点
        NodeList nodeList = parser.extractAllNodesThatMatch(filter);
        //遍历
        for (int i = 0; i < nodeList.size(); i++) {
            Node node = nodeList.elementAt(i);
            System.out.println(((LinkTag)node).getLink());
        }
    }
}

4.2、案例二

使用 Parser(String resource)构造方法实例化 Parser,并使用多个过滤器的“与”操作来 获取节点链接和节点标签内的数据

public class HTMLPaserTest2 {
    public static void main(String[] args) throws IOException, ParserException {
        //实例化Parser,用网页的URL作为参数
        Parser parser = new Parser("https://www.runoob.com");
        //设置网页的编码
        parser.setEncoding("utf8");
        //过滤页面中的便签
        NodeFilter filtertag = new TagNameFilter("div");
        //父节点包含div
        NodeFilter filterParent = new HasParentFilter(filtertag);
        //包含a标签
        NodeFilter filtername = new TagNameFilter("a");
        //过滤器的【并】操作
        NodeFilter filter = new AndFilter(filterParent, filtername);
        //选择匹配到的内容
        NodeList list = parser.extractAllNodesThatMatch(filter);
        //遍历
        for (int i = 0; i < list.size(); i++) {
            Node node = list.elementAt(i);
            System.out.println(((LinkTag)node).getLink());
        }
    }
}

4.3、案例三

使用的是 Parser(URLConnection connection) 构造方法实例化 Parser。同时,基于 CSS 选择器进行过滤。

public class HTMLParserTest3 {
    public static void main(String[] args) throws IOException, ParserException {
        //使用URLConnection请求数据
        URL url = new URL("https://www.runoob.com");
        URLConnection conn = url.openConnection();
        Parser parser = new Parser(conn);
        //使用CSS选择器进行过滤操作
        CssSelectorNodeFilter filter = new CssSelectorNodeFilter("body > div.container.main > div > div.col.middle-column-home > div.codelist.codelist-desktop.cate1 > a");
        //选择匹配到的内容
        NodeList list = parser.extractAllNodesThatMatch(filter);
        System.out.println(list.size());
        //遍历
        for (int i = 0; i < list.size(); i++) {
            Node node = list.elementAt(i);
            System.out.println(((LinkTag)node).getLink());
        }
    }
}
Logo

北京人形旗下天工造物具身智能开源社区,聚焦具身天工与慧思开物两大平台

更多推荐