爬虫配置必备:JQuery|querySelector|Cheerio DOM节点选择干货集

作者:fbysss

QQ:溜酒酒吧酒吧吾散

blog:blog.csdn.net/fbysss

声明:本文由fbysss原创,转载请注明出处


前言

网页爬取,是一项既费脑子又繁琐的工作。因为网页格式不一,很难完全靠机器自动识别。

通常,我们可以采用css选择器来选取DOM节点,从整个网页中抽取我们需要的内容。

前端大家最熟悉的应该是JQuery了。如果JQuery不好用,可以直接使用原生的document.querySelectorAll,现在的浏览器大多也都支持了。

如果是Nodejs爬虫,一般采用cheerio模块(可以理解为后端的JQuery)来解析DOM。

cheerio虽然高仿JQuery,但还是有些差异,而且一些特性尚未实现。尽量更新到最新版本。

这里并不罗列所有的表达式,而是重点记录一些DOM选择和相关工作方法。

前端的例子中也都是cheerio都支持的表达式,测试环境都是chrome。

表达式

1.简单表达式

document.querySelectorAll("div");//标签
document.querySelectorAll(".classA");//单个类
document.querySelectorAll("#idA");//id选择器

2.层级关系

document.querySelectorAll("div span");
document.querySelectorAll("div span .classA");

3.多个类

document.querySelectorAll(".classA.classB");
document.querySelectorAll("class=['classA classB']");//中括号中如果有空格,必须加引号

4.多选(or关系)

document.querySelectorAll(".classA,.classB");
 
  

"#article,.description"不行,cheerio中只能使用".description,#article"

5.下一个元素

document.querySelectorAll.('h1+figure')  //选择h1后面的figure元素

6.有特殊符号

document.querySelectorAll("div[class=tw:classA]");

7.通配符

document.querySelectorAll("input[id^='code']");//id属性以code开始的所有input标签
document.querySelectorAll("input[id$='code']");//id属性以code结束的所有input标签
document.querySelectorAll("input[id*='code']");//id属性包含code的所有input标签


8.不等于

document.querySelectorAll("div:not([id^=\"blog\"])");//不等于

cheerio示例:

var cheerio=require("cheerio");
var str='
fbysss
'; var $=cheerio.load(str); var len = $("div:not([class$=\"Color\"])").length; console.log("len is :",len);
9.忽略大小写

还以上面的例子

var len = $("div:not([class$=\"Color\"])").length;更换为

var len = $("div:not([class$=\"color\" i])").length;即可。——\为转义字符,当多层嵌套,单引号双引号都用尽的时候需要

参考:

http://stackoverflow.com/questions/5671238/css-selector-case-insensitive-for-attributes

10.选择文本节点

$(elem)
  .contents()
  .filter(function() {
    return this.nodeType === 3; //Node.TEXT_NODE
  });

11.选择注释节点

var cheerio = require('cheerio');
var str ="  
"; var $ = cheerio.load(str); $.root().find('*').contents().filter(function(){ return this.nodeType == 8;}).length;//注意,这里是2 var str2 = "
"+str+"
"; $ = cheerio.load(str2); $.root().find('*').contents().filter(function(){ return this.nodeType == 8;}).length;//4.如果要删除所有的注释节点,需要在字符串前面添加一个根节点
$.root().find(*)也可以直接使用$(*)



12.chrome中显示的问题:

在最新的chrome版本中,console的显示出现了变化。选择一个节点,如果使用document.querySelectorAll,返回一个节点时,需要使用[0]才行,否则就是返回一个很大的节点,很不直观。比如:document.querySelectorAll("div")[0]


对于多个节点,只能这么写了:

var cates = document.querySelectorAll('.article-title-link');
[].forEach.call(cates,function(cate){console.log(cate.href)}) 或者[].forEach.call(cates,function(cate){console.log(cate)})


还有更好的写法:
document.querySelectorAll('.article-title-link').forEach(function(cate){console.log(cate)})

其他遇到的问题解决:

1.chrome突然怎么都打不出东西来了。原来是一个选项的问题。在上方,勾选all,原来选择了error所以不显示。

2.JQuery:上述例子,前端都是以document.querySelectorAll、后端以cheerio举例。

如果前端要使用JQuery,需要注意,有的网站可以,有的则不行,这和浏览器支持的JQuery版本、不同网站引用的JQuery版本有关。

如果出现无法选择的情况,可以先在console中测试:$().jquery可以检查当前的jquery版本

尝试运行以下代码:

var jq = document.createElement('script');
jq.src = "http://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js";
document.getElementsByTagName('head')[0].appendChild(jq);
jQuery.noConflict();

对于https网页,需要把http修改为https否则可能报错:
VM273:4 Mixed Content: The page at 'https://countrycode.org/' was loaded over HTTPS, but requested an insecure script 'http://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js'. This request has been blocked; the content must be served over HTTPS. 


结语

上面都是本人在爬虫配置过程中,总结的经验,相信对于从事网页抓取工作的同学,会有很好的帮助。


你可能感兴趣的:(互联网)