在编写不同爬虫时我们使用Beautiful Soup,pyquery,正则等对数据进行提取,他们很方便实用。但是在Scrapy中,他也是提供了内置选择器的,下面我们来学习一下。
在scrapy中我们想要对提取的数据进行调试,也就是判断提取内容是否正确,我们可以使用scrapy提供的交互式命令行 scrapy shell
本次我们以古诗文网作为案例进行测试,获取其中古诗文部分内容。
在终端我们输入scrapy shell https://www.nulog.cn/mingju/
之后特就会自动下载网页并返回response,我们可以对其进行操作。
scrapy中的xpath和普通xpath用法一样,这里列举几个常用的规则
表达式 | 描述 |
---|---|
节点名称 | 选取此节点的所有子节点 |
/ | 从当前节点选取直接子节点 |
// | 从当前节点选取子孙节点 |
. | 选取当前节点 |
… | 选取当前节点的父节点 |
[@属性=“属性值”] | 选取属性 |
text() | 文本获取 |
@属性 | 属性获取 |
首先我们在浏览器的检查界面,找到我们需要的数据的位置
通过图片我们可以看到已经出现了我们想要的内容,接下来我们对其进行提取
我们先分步进行,每一步完成我们可以输出看一下返回的是什么:
#1.选择整个内容框,利用器class属性进行匹配
res = response.selector.xpath('//ul[@class="mingju"]')
res输出:['//ul[@class="mingju"]' data=' data=',……]
#3.上一步中我们已经选取了包含内容的直接节点,接下来我们就要取到其中的内容
res3 = res2.xpath('./text()')
res3输出:['./text()' data='清水出芙蓉,天然去雕饰'>,
'./text()' data='西施越溪女,出自苎萝山'>,……]
#4.第三步中我们发现结果还是SelectorList类型,并不是纯内容,我们使用getall()方法获取
res4 = res3.getall()
res4输出:['清水出芙蓉,天然去雕饰','西施越溪女,出自苎萝山',……]
#假如我们只想获取第一个内容,还提供给我们另一个方法get()
res5 = res3.get()
res5输出:'清水出芙蓉,天然去雕饰'
接下来我们将以上步骤合并一步提取
res=response.xpath('//ul[@class="mingju"]/li/h3/a/text()').getall()
上面我们就完成了使用xpath进行提取的过程。
注意:如果仔细观察,会发现上面代码中我们使用response.selector.xpath()和response.xpath()效果是一样的。的确如此,两种效果相同,后者是scrapy给我们提供的前者的快捷方式,方便实用。下面的css选择器同理,今后为了方便,将统一使用后者。
表达式 | 描述 |
---|---|
节点名 | 直接选取该节点 |
::text | 获取文本 |
::attr(属性名) | 获取属性 |
[属性=“属性值”] | 匹配属性 |
还是上面的例子
#1.找到响应的结点
res = response.css('ul[class="mingju"] li h3 a')
#2.获取文本
res2 = res.css('::text')
#3.提取内容
res3 =res2.getall()
#一步完成
res = response.css('ul[class="mingju"] li h3 a::text').getal
l()
加入我们提取的文本还不满足要求我们可以利用正则继续提取,类似于get()和getall(),有re()
和re_first()
.需要注意的是response不能直接调用,需要配合xpath和css
#取上半句
#搭配css,
res = response.css('ul[class="mingju"] li h3 a::text').re('(.*?),.*?')
#搭配xpath
res=response.xpath('//ul[@class="mingju"]/li/h3/a/text()').re_first('(.*?),.*?')
选择器之间可以嵌套使用
res = response.xpath('//ul[@class="mingju"]').css('li h3 a::te
xt').re('(.*?),.*?')
以上便是选择器的用法,日后我们将使用他们对数据进行提取,大大提高我们的效率。