Veiking百草园


老狗啃爬虫-爬虫必知基础Jsoup和Xsoup

老狗啃骨头   @Veiking   2020-12-06

老狗啃爬虫-爬虫必知基础Jsoup和Xsoup

摘要:

爬虫爬取内容,本质就是把网站页面下载、读取过来,然后其核心工作就是解析定位,提取数据。这里说的Jsoup、Xsoup、CSS选择器、Xpath、JsonPath,包括正则表达式的应用,都是数据处理过程中必不可少的基础性技术。我们使用的爬虫框架WebMagic,是使用Jsoup作为HTML解析工具的,还有基于Jsoup升级了能解析XPath的工具Xsoup

  我们一般所说的爬虫抓取内容,其本质类似于将网页下载下来,然后通过对HTML元素的解析遍历,对目标数据进行定位获取,所以,这里有个重点,就是对HTML元素的操作。

数据的定位

  这里先顺带说一嘴,我们使用的爬虫框架WebMagic,是使用Jsoup作为HTML解析工具的,还有基于Jsoup升级了能解析XPath的工具Xsoup。
  此外,对于的数据的处理方面,还有类似于Xpath的JsonPath语言,是用来帮助处理json数据的,还有正则表达式,我们都是要了解了解的。

Jsoup

  jsoup是一个用于处理HTML的优秀插件。其使用HTML5最佳DOM方法和CSS选择器,并为抓取页面上的URL和提取处理页面数据提供了非常方便的API。我们看下边得例子:

Document document = Jsoup.connect("http://www.aigufeng.com/").get();
String title = document.title();

  如此,我们就可以得到这个爱古风首页的title;
  接下来再看下边的例子:

Document document = Jsoup.connect("http://www.aigufeng.com/celebrity/column-suitang/list.html").get();
Elements celebrityList= document.select("#content .contents_list ul > li h2 a");
for (Element celebrity: celebrityList) {
    String title = celebrity.data();
}

  这样,我们就可以得到一个列表页的提取出来的title信息。
  注意,我们看这个select(),这是css选择器的应用,用来帮助定位元素信息的,就像上边的代码,表示的就是,找出id为content的属性为contents_list元素的这个ul列表下的…a元素,这样基本就是跟html元素的门牌号一样,精准定位到我们想要的一个或一类元素信息。

Xsoup

  虽然说jsoup已经很不错了,但是人们总是在追求更好方案的路上永不停息,Xsoup就是这种追求的结果。Xsoup是基于Jsoup开发的HTML抽取插件,其主要特点就是支持XPath。XPath是一种在 XML、HTML文档中定位查找信息的表达式语言,可以帮助对HTML文件元素和属性进行快速遍历和定位。
  同样的工作结果,我们看看Xsoup是怎么处理的:

Document document = Jsoup.connect("http://www.aigufeng.com/").get();
String title = Xsoup.compile("/html/head/title").evaluate(document).get();
这样即可以得到页面的title;
Document document = Jsoup.connect("http://www.aigufeng.com/celebrity/column-suitang/list.html").get();
List titleList= Xsoup.compile("//*[@id="content" and @class='title']/text()").evaluate(document).list();

for (String title: titleList) {
    String title = title;
}

  通过上面的代码,我们就可以得到页面列表的title信息。
  Xsoup不是jsoup的替代,而是基于其的技术升级,一般用的时候都是一起结合着使用的。
  现在还有一个更强大的XPath解析器,Saxon,据说支持XPath 2.0语法,但目前应用还不是很广泛,原理都一样,感兴趣的可以研究下。

JsonPath

  JsonPath是跟Xpath功能上很类似的一个语言,它用于从Json中快速定位内容。
  在我们开发爬虫,实际使用过程中,可能会出现对页面数据处理提取,存储后二次处理的,亦可能直接从网站一些接口调用到的就是json形式的数据,所以处理json也是经常出现的场景,我们看个例子:
  这里有一个json数据:

{
    "store":{
        "website":[
            {
                "category":"information",
                "url":"http://www.acesoon.com",
                "title":"安讯网",
                "attribute":"test"
            },
            {
                "category":"tools",
                "url":" http://www.aigufeng.com ",
                "title":"爱古风",
                "attribute":"test"
            }
        ],
        "toys":{
            "product":"Teenie",
            "color":"yellow",
            "attribute":"gift"
        }
    }
}

  用JsonPath怎么定位取用上边json里的数据呢,我们看下边的代码:

String json = "{…}"; // 如上示
Object document = Configuration.defaultConfiguration().jsonProvider().parse(json);
String website0= JsonPath.read(document, "$.store.website[0].title");
String website1 = JsonPath.read(document, "$.store.website[1].title");
String toys = JsonPath.read(document, "$.store.toys.product");

  这样,我们就可以通过层级关系,按照数据的结构路径定位,获取到我们想要的数据。
  结合Xpath,我们收集整理JsonPath与Xpath类似功能的一个语法对照表,大家可以感受下:

XPath JSONPath Description
/ $ 表示根元素
. @ 当前元素
/ . or [] 子元素
.. n/a 父元素
// .. 递归下降,JSONPath是从E4X借鉴的。
* * 通配符,表示所有的元素
@ n/a 属性访问字符
[] [] 子元素操作符
| [,] 连接操作符在XPath 结果合并其它结点集合。JSONP允许name或者数组索引。
n/a [start:end:step] 数组分割操作从ES4借鉴。
[] ?() 应用过滤表示式
n/a () 脚本表达式,使用在脚本引擎下面。
() n/a Xpath分组

  从表格可以看出来,二者之间很多表现形式,其底层逻辑基本是一样的。
  当然,Xpath和JsonPath毕竟使用在不同的场景上的,他们还有很多具体细节上操作的语法、函数等,还是有很大不同的,这个以后在使用的过程中,我们再慢慢发掘。

正则表达式

  正则表达式则是一种通用的文本抽取语言。我们在爬虫的开发中,应用最多的地方就是这个url的规则匹配。
  当我们在一个页面上提取url的时候,除了一些有规律可循、抓取起来有意义的目标链接,可能还有很多内链啊外链啊等,各种干扰,这时候我们不能一股脑都拿过来,就得用一定的规则去匹配,符合条件的url,才是我们的目标,这时候就是正则表达式大显身手的时候。
  正则表达式是一个应用非常普遍的基础性技术,这里不是重点,就这么提一嘴。

总结

  爬虫爬取内容,本质就是把网站页面下载、读取过来,然后其核心工作就是解析定位,提取数据。这里说的Jsoup、Xsoup、CSS选择器、Xpath、JsonPath,包括正则表达式的应用,都是数据处理过程中必不可少的基础性技术。
  好了,以上列举的这些技术概念,感兴趣可以深入研究下,我们在之后的开发学习过程中,需要的时候,即用即看。


老狗啃骨头



慷慨发言

(您提供的信息将用于后续必要的反馈联系,本站会恪守隐私)

潜影拾光

老子坐清源

天地不仁,以万物为刍狗。

扫码转发

二维码
二维码
二维码
二维码
二维码
二维码

博文标签