Python网路爬虫数据采集实战:网页解析库

优采云 发布时间: 2020-08-15 09:20

   在了解爬虫基础、请求库和正则匹配库以及一个具体豆瓣影片爬虫实例以后,可能你们还对超长的正则表达式记忆犹新,设想假如想要匹配的条目愈发多那表达式宽度将会愈发惊悚,这或许不是我们想要的,因此本文介绍的解析库可以帮助我们愈发轻松地提取到特定信息。

  目录

  一、Xpath库1.库简介

  XPath(XML Path Language)即XML路径语言,它是一门在XML文档中查找信息的语言,但它同样适用于HTML 文档的搜索。所以在做爬虫时,我们完全可以使用XPath 来做相应的信息抽取。

  2.入门测试

  需要导出lxml库(若未安装推荐用pip install lxml安装即可),然后使用下边代码进行简单测试:

  

from lxml import etreetext = ''' first second third fourth '''html = etree.HTML(text)result = etree.tostring(html)print(result.decode('utf-8'))​

  结果如下:可以看见,etree模块除了将缺乏的标签闭合了,而且还加上了html、body节点。

  

first second third fourth

  3.基本技巧

  xpath的常用规则及基本方式如下:

  表达式描述

  nodename

  选取此节点的所有子节点。

  /

  从根节点选定。

  //

  从匹配选择的当前节点选择文档中的节点,而不考虑它们的位置。

  .

  选取当前节点。

  ..

  选取当前节点的父节点。

  @

  选取属性。

  上文中的入门测试即为初始化html。其中etree.parse()是初始化html构造一个XPath解析对象;etree.tostring()是修补html文件中代码,把缺的头或尾节点补足;result.deode('utf-8')修复后的HTML代码是字节类型,转化成字符串。

  

print(html.xpath('//*')) # 获取所有的节点print(html.xpath('//li')) # 获取所有li节点

  

print(html.xpath('//li/a')) # 所有li下是所有直接a子节点print(html.xpath('//ul//a')) # 所有ul下的子孙a节点

  

# 找到所有a节点中href为links.html的父节点的class值# .. 来实现查找父节点print(html.xpath('//a[@href="link1.html"]/../@class'))​

  

# 找到class值为item-0是节点print(html.xpath('//li[@class="item-0"]'))

  

# 匹配到class值为item-0节点中的a标签中的文本print(html.xpath('//li[@class="item-0"]/a/text()'))

  

print(html.xpath('//li/a/@href')) # 找到li下a中的href属性值

  

#只要节点属性class中包含item就能匹配出来print(html.xpath('//li[contains(@class,"item")]/a/text()'))

  二、BeautifulSoup库1.库简介

  BeautifulSoup4和 lxml 一样,Beautiful Soup 也是一个HTML/XML的解析器,主要的功能也是怎么解析和提取HTML/XML 数据。BeautifulSoup支持Python标准库中的HTML解析器,还支持一些第三方的解析器,如果我们不安装它,则 Python 会使用 Python默认的解析器,lxml解析器愈发强悍,速度更快,推荐使用lxml 解析器。

  

  2.入门测试

  假设有这样一个Html(即从百度网页源代码截取一段),具体内容如下:

  

html = ''' 百度一下,你就知道 新闻 hao123 地图 视频 贴吧 更多产品 '''

  如果将字符串单独保存为html文件,则使用谷歌浏览器打开后即为:

  

  通过导出bs4库中的BeautifulSoup子类可以输入以下命令观察输出:

  

from bs4 import BeautifulSoup bs = BeautifulSoup(html,"html.parser") # 缩进格式print(bs.prettify()) # 获取title标签的所有内容print(bs.title) # 获取title标签的名称print(bs.title.name) # 获取title标签的文本内容print(bs.title.string) # 获取head标签的所有内容print(bs.head) # 获取第一个div标签中的所有内容print(bs.div) # 获取第一个div标签的id的值print(bs.div["id"]) # 获取第一个a标签中的所有内容print(bs.a) # 获取所有的a标签中的所有内容print(bs.find_all("a")) # 获取id="u1"print(bs.find(id="u1")) # 获取所有的a标签,并遍历打印a标签中的href的值for item in bs.find_all("a"): print(item.get("href")) # 获取所有的a标签,并遍历打印a标签的文本值for item in bs.find_all("a"): print(item.get_text())

  3.基本技巧

  BeautifulSoup4将复杂HTML文档转换成一个复杂的树状结构,每个节点都是Python对象,所有对象可以归纳为4种:

  

# [document] #bs 对象本身比较特殊,它的 name 即为 [document]print(bs.name) # head #对于其他内部标签,输出的值便为标签本身的名称print(bs.head.name) # 在这里,我们把 a 标签的所有属性打印输出了出来,得到的类型是一个字典。print(bs.a.attrs) #还可以利用get方法,传入属性的名称,二者是等价的print(bs.a['class']) # 等价 bs.a.get('class')# 可以对这些属性和内容等等进行修改bs.a['class'] = "newClass"print(bs.a) # 还可以对这个属性进行删除del bs.a['class'] print(bs.a)

  

print(bs.title.string) print(type(bs.title.string))

  

print(type(bs.name)) print(bs.name) print(bs.attrs)

  

print(bs.a)# 此时不能出现空格和换行符,a标签如下:# print(bs.a.string) # 新闻print(type(bs.a.string)) # 连接也可以,但是加>只能查找子元素,空格子孙元素

  3.基本技巧

  

# 字符串初始化:from pyquery import PyQuery as pqdoc=pq(html)print(doc('li'))# URL初始化doc=pq(url="https://ww.baidu.com")print(doc)​a = open('test.html','r',encoding='utf8')doc=pq(a.read())print(doc)

  

# id 为container,class为list下的所有liprint(doc('.head_wrapper #u1 a'))

  

# .find():查找所有子孙节点items = doc('#u1')print(items.find('a'))​# .children():查找子节点items=doc('#u1')print(items.children('.mnav'))​# 父节点doc=pq(html)items=doc('.mnav')print(items.parent())print(items.parents())# 兄弟节点doc=pq(html)li=doc('.mnav')print(li.siblings('.bri'))

  

# 用items()函数生成列表*敏*感*词*进行遍历doc=pq(html)lis=doc('a').items()for li in lis: print(li)

  

# 获取属性a=doc('.head_wrapper #u1 .bri')# attr只会输出第一个a节点属性,要用items()遍历print(a.attr('href'))# 获取文本# .text()a=doc('.head_wrapper #u1 .bri')# text()函数会输出所有的li文本内容print(a.text())# .html()li=doc('a')# html()只会输出第一个li节点内的HTML文本print(li.html())

  

# removeClass addClassa=doc('.head_wrapper #u1 .bri')print(a)a.removeClass('bri') # 移除active的classprint(a)a.addClass('bri') # 增加active的classprint(a)​# attr text htmla.attr('name','link') # 增加属性name=linka.text('changed item') # 改变文本 changed itema.html('changed item ') # 改变HTMLprint(a)​ # remove()u1=doc('#u1')# 删除wrap中p节点u1.find('a').remove()print(u1.text())

  Python有关Xpath、BeautifulSoup、pyquery三大解析库的基本使用方式介绍至此结束,下文开始介绍动态网页数据采集的相关库与实战,前文涉及的基础知识可参考下边链接:

  Python网路爬虫数据采集实战:基础知识

  Python网路爬虫数据采集实战:Requests和Re库

  Python网路爬虫数据采集实战:豆瓣影片top250爬取

0 个评论

要回复文章请先登录注册


官方客服QQ群

微信人工客服

QQ人工客服


线