飞道的博客

解析网页--xpath-python爬虫知识点5

332人阅读  评论(0)

  • 正则表达式相当于一个模板
  • 而xpath解析网页 提取数据
  • 不同网页结构 我们灵活采用不同的技术
  • html 超文本标记语言,<> 标识
    xml 可扩展标记语言 除了标识,也可以用于简单的数据存储
    lxml 是一个python的模块,html 网页源代码,不能用xpath,把html文本转化成xml对象,就可以使用xpath进行解析

一、xpath介绍

基本概念

  • XPath(XML Path Language)是一种XML的查询语言,他能在XML树状结构中寻找节点。XPath 用于在 XML 文档中通过元素和属性进行导航
  • xml是一种标记语法的文本格式,xpath可以方便的定位xml中的元素和其中的属性值。lxml是python中的一个第三方模块,它包含了将html文本转成xml对象,和对对象执行xpath的功能
  • xpath就是一种可以很久地址找到人的技术 确定路径

html、xml 与 lxml

  • html 超文本标记语言,<> 标识
    xml 可扩展标记语言 除了标识,也可以用于简单的数据存储
    lxml 是一个python的模块,html 网页源代码,不能用xpath,把html文本转化成xml对象,就可以使用xpath进行解析

作用

  • 解决一些网页结构明显的数据解析

节点关系分析

xml_content = '''
<bookstore>
<book>
    <title lang='eng'>Harry Potter</title>
    <author>JK.Rowing</author>
    <year>2005</year>
    <price>29<price>
</book>
</bookstore>
'''

  • 父(Parent) book元素是title、author、year、price元素的父
    子(Children) title、author、year、price都是book元素的子
    同胞(Sibling) title、author、year、price都是同胞
    先辈(Ancestor) title元素的先辈是 book元素和bookstore元素

二、xpath helper 网页工具

工具安装

  • 网页的工具可以帮助我们更好的写xpath的结构
  • 先通过xpath了解关系,再利用xpath进行内容获取

语法

  • 查找某个特定的节点或者包含某个指定的值的节点

使用

  • 重启浏览器,快捷键CTRL+SHIFT+X开启XPath Helper插件;
    长按CTRL+SHIFT,鼠标指向需提取的段落,按X开启或关闭提取,提取到的段落会变为黄色。

    点到element的信息区域,也可以参考这里给的xpath路径

三、python模块的使用

  • 在Python中,我们安装lxml库来使用XPath 技术
  • lxml 可以⾃动修正 html 代码
  • 使用 pip 安装:pip install lxml
  • lxml 是 一个HTML/XML的解析器,主要的功能是如何解析和提取HTML/XML数据

etree.HTML

  • from lxml import etree
  • 利用etree.HTML,将字符串转化为Element对象
wb_data = requests.get(url_base,params=kw,headers=headers).content.decode('utf-8')
html_element = etree.HTML(wb_data)

xpath

  • 对Element对象数据结果进行xpath操作
temList = html_element.xpath('//div[@class="info"]')

四、xpath案例-豆瓣电影TOP250

  • 页码规律
    https://movie.douban.com/top250
    https://movie.douban.com/top250?start=25
  • 因为有部分电影并没有所以信息都有,所以如果你把一页全部电影的某个信息爬下来的话,就会导致序号混乱
  • 所以对于这类的还是把一个电影的信息全部爬下来,在这里就可以添在判断条件,如果为None就返回‘’,这样占位,然后爬一页25部电影的,再爬10页的
  • 会用到两个for循环
import requests
import csv
from lxml import etree


headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.128 Safari/537.36'
}


class doubanmovieTop250():
    def getSource(self,page):
        url_base = 'https://movie.douban.com/top250?'
        kw = {'start':str(25*page)}
        wb_data = requests.get(url_base,params=kw,headers=headers).content.decode('utf-8')
        return wb_data
    
    def parseSource(self,page):
        html_element = etree.HTML(self.getSource(page))
        movieItemList = html_element.xpath('//div[@class="info"]')
        movieList = []
        for i,eachMoive in enumerate(movieItemList):
            title = eachMoive.xpath('div[@class="hd"]/a/span[@class="title"]/text()') # 标题
            link = eachMoive.xpath('div[@class="hd"]/a/@href')[0] # url
            massage = eachMoive.xpath('div[@class="bd"]/p[@class=""]/text()') 
            detail = massage[1].split('\xa0/\xa0') 
            year = detail[0].strip()   #年份
            country = detail[1].strip() #国家
            tag = detail[2]  #剧情标签
            star = eachMoive.xpath('div[@class="bd"]/div[@class="star"]/span[@class="rating_num"]/text()')[0] # 评分
            rank_num = eachMoive.xpath('div[@class="bd"]/div[@class="star"]/span[last()]/text()')[0]  #  # 评分人数
            quote = eachMoive.xpath('div[@class="bd"]/p[@class="quote"]/span/text()') # 引言(名句)
            # 第一种异常处理
            # 第二种非空判断
            if quote:
                quote = quote[0]
            else:
                quote = ''
            if len(title)<2:
                title.append('    ')
            movieList.append((page*25+i+1,title[0],title[1][3:],massage[0][29:].replace('\xa0',''),year,country,tag,link,star,rank_num,quote))
        return movieList
        
    def saveData(self):
        header = ['排名','片名','副片名','人物','年份','国家','剧情','豆瓣链接','豆瓣评分','评分人数','豆瓣引言']
        with open('doubanmovie_Top250.csv','w',encoding='utf-8',newline='') as file_obj:
            writer = csv.writer(file_obj)
            writer.writerow(header)
            for page in range(10):
                writer.writerows(self.parseSource(page))


def main():
    doubanmovieTop250().saveData()
    
    
if __name__ == '__main__':
    main()


转载:https://blog.csdn.net/weixin_43761516/article/details/116308865
查看评论
* 以上用户言论只代表其个人观点,不代表本网站的观点或立场