Jsoup代码解读之五-实现一个CSS Selector
Jsoup代码解读之七-实现一个CSS Selector
当当当!终于来到了Jsoup的特色:CSS Selector部分。selector也是我写的爬虫框架webmagic开发的一个重点。附上一张street fighter的图,希望以后webmagic也能挑战Jsoup!
select机制
Jsoup的select包里,类结构如下:

在最开始介绍Jsoup的时候,就已经说过NodeVisitor和Selector了。Selector是select部分的对外facade,而NodeVisitor则是遍历树的底层API,CSS Selector也是根据NodeVisitor实现的遍历。
Jsoup的select核心是Evaluator。Selector所传递的表达式,会经过QueryParser,最终编译成一个Evaluator。Evaluator是一个抽象类,它只有一个方法:
public abstract boolean matches(Element root, Element element);
注意这里传入了root,是为了某些情况下对树进行遍历时用的。
Evaluator的设计简洁明了,所有的Selector表达式单词都会编译到对应的Evaluator。例如#xx对应Id,.xx对应Class,[]对应Attribute。这里补充一下w3c的CSS Selector规范:http://www.w3.org/TR/CSS2/selector.html
当然,只靠这几个还不够,Jsoup还定义了CombiningEvaluator(对Evaluator进行And/Or组合),StructuralEvaluator(结合DOM树结构进行筛选)。
这里我们可能最关心的是,“div ul li”这样的父子结构是如何实现的。这个的实现方式在StructuralEvaluator.Parent中,贴一下代码了:
static class Parent extends StructuralEvaluator {
public Parent(Evaluator evaluator) {
this.evaluator = evaluator;
}
public boolean matches(Element root, Element element) {
if (root == element)
return false;
Element parent = element.parent();
while (parent != root) {
if (evaluator.matches(root, parent))
return true;
parent = parent.parent();
}
return false;
}
}
这里Parent包含了一个evaluator属性,会根据这个evaluator去验证所有父节点。注意Parent是可以嵌套的,所以这个表达式"div ul li"最终会编译成And(Parent(And(Parent(Tag("div")),Tag("ul")),Tag("li")))这样的Evaluator组合。
select部分比想象的要简单,代码可读性也很高。经过了parser部分的研究,这部分应该算是驾轻就熟了。
关于webmagic的后续打算
webmagic是一个爬虫框架,它的Selector是用于抓取HTML中指定的文本,其机制和Jsoup的Evaluator非常像,只不过webmagic暂时是将Selector封装成较简单的API,而Evaluator直接上了表达式。之前也考虑过自己定制DSL来写一个HTML,现在看了Jsoup的源码,实现能力算是有了,但是引入DSL,实现只是一小部分,如何让DSL易写易懂才是难点。
其实看了Jsoup的源码,精细程度上比webmagic要好得多了,基本每个类都对应一个真实的概念抽象,可能以后会在这方面下点工夫。
Jsoup代码解读之五-实现一个CSS Selector的更多相关文章
- Jsoup代码解读之一-概述
Jsoup代码解读之一-概述 今天看到一个用python写的抽取正文的东东,美滋滋的用Java实现了一番,放到了webmagic里,然后发现Jsoup里已经有了…觉得自己各种不靠谱啊!算了,静下心来学 ...
- Jsoup代码解读之二-DOM相关对象
Jsoup代码解读之二-DOM相关对象 之前在文章中说到,Jsoup使用了一套自己的DOM对象体系,和Java XML API互不兼容.这样做的好处是从XML的API里解脱出来,使得代码精炼了很多 ...
- Jsoup代码解读之六-防御XSS攻击
Jsoup代码解读之八-防御XSS攻击 防御XSS攻击的一般原理 cleaner是Jsoup的重要功能之一,我们常用它来进行富文本输入中的XSS防御. 我们知道,XSS攻击的一般方式是,通过在页面输入 ...
- Jsoup代码解读之四-parser
Jsoup代码解读之四-parser 作为Java世界最好的HTML 解析库,Jsoup的parser实现非常具有代表性.这部分也是Jsoup最复杂的部分,需要一些数据结构.状态机乃至编译器的知识.好 ...
- Jsoup代码解读之三-Document的输出
Jsoup代码解读之三-Document的输出 Jsoup官方说明里,一个重要的功能就是output tidy HTML.这里我们看看Jsoup是如何输出HTML的. HTML相关知识 分析代码前 ...
- 如何判断一个DOM元素正在动画,一个CSS“阻塞”JS的例子
一般情况下CSS不会直接影响JS的程序逻辑,但是以CSS实现动画的话,这个便不太确定了,这个故事发生在与UED迁移全局样式的过程. 曾经我有一段实现弹出层隐藏动画的代码是这个样子的: if (this ...
- 转:Selenium之CSS Selector定位详解
CSS selector定位 CSS(Cascading Style Sheets)是一种语言,它被用来描述 HTML 和 XML 文档的样式. 百度输入框: <input name=&quo ...
- css selector
文章一: http://www.jb51.net/css/68287.html 去年我学jQuery的时候,曾经做过一点选择器(selector)的笔记,今天是CSS的选择器,以后还有一部分xPath ...
- Xpath 和Css Selector使用
Xpath是xml的路径语言,就是通过元素的路径来查找标签元素. Xpath直接在火狐浏览器的firebug中练习,49版本一下的火狐才能用firebug插件. Xpath的使用方法 注://* ...
随机推荐
- 节点与坐标系——Cocos2d-x学习历程(十)
1.Node Cocos2d-x把渲染树上的每一个游戏元素抽象为一个节点,即Node.一切游戏元素都继承自Node,因此它们都具有Node所提供的特性.Node定义了一个可绘制对象的通用特性,包括位置 ...
- 加密传输SSL协议3_非对称加密
困死了,这里对非对称加密体系开个头,具体的实验明天写 非对称加密体系 为了解决对称加密中密钥的传输的问题,一些天才的数学家就提出了非对称式的加密体系,也称为公钥加密体系. 加密和解密的密钥是不同的.一 ...
- 查看mysql字符集及修改表结构
MySQL 乱码的根源是的 MySQL 字符集设置不当的问题,本文汇总了有关查看 MySQL 字符集的命令.包括查看 MySQL 数据库服务器字符集.查看 MySQL 数据库字符集,以及数据表和字段的 ...
- Linux网络管理——子网掩码
1. 网络基础 .note-content {font-family: "Helvetica Neue",Arial,"Hiragino Sans GB",&q ...
- HTML DOM 属性记录
将HTML DOM中几个容易常用的属性做下记录,需要的朋友可以参考下. nodeName.nodeValue 以及 nodeType 包含有关于节点的信息. nodeName 属性含有某个节点 ...
- 【grunt整合版】学会使用grunt打包前端代码
grunt 是一套前端自动化工具,一个基于nodeJs的命令行工具,一般用于:① 压缩文件② 合并文件③ 简单语法检查 对于其他用法,我还不太清楚,我们这里简单介绍下grunt的压缩.合并文件,初学, ...
- Octopress创建GitHub Pages——基于代码托管的静态博客
Github Pages是静态网页来的,官方也半认可了它的博客用途,代码挂在github上,随时都可以更改,算是不错的一种尝试,因为它是静态的,所以在表现上会自由得多,但是,同样因为它是静态的,管理上 ...
- larbin源码之global.h
/** This represent a connection : we have a fixed number of them * fetchOpen links them with servers ...
- 数据库中字段类型对应C#中的数据类型
数据库中字段类型对应C#中的数据类型:数据库 C#程序 int int32 text string bigint int64 binary System.Byte[] bit Boolean char ...
- 【Windows 8 Store App】学习三:HTTP
原文 http://www.cnblogs.com/java-koma/archive/2013/05/22/3093309.html 1,HttpClient Win 8提供了System.Net. ...