爬虫之xpath解析

xpath

1、相关安装

安装lxml
在python Terminal终端安装

pip install lxml

谷歌浏览器xpath插件安装
文件链接
链接:https://pan.baidu.com/s/1YOeSPWFqZCrfXsC_B4ZlqQ
提取码:d7st
首先建一个空文件夹,将压缩包解压到此文件夹
在这里插入图片描述
然后打开谷歌浏览器
在这里插入图片描述
然后加载文件夹
在这里插入图片描述
加载完后重启一下浏览器
在这里插入图片描述
当右键检查页面的时候,使用快捷键ctrl+shift+x启动此插件
在这里插入图片描述
xpath使得正则匹配等方式爬取网页更加方便

2、一个测试用的html页面

test.html

<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8" />
	<title>测试页面</title>
</head>
<body>
	<ol>
		<li class="haha">醉卧沙场君莫笑,古来征战几人回</li>
		<li class="heihei">两岸猿声啼不住,轻舟已过万重山</li>
		<li id="hehe" class="nene">一骑红尘妃子笑,无人知是荔枝来</li>
		<li class="xixi">停车坐爱枫林晚,霜叶红于二月花</li>
		<li class="lala">商女不知亡国恨,隔江犹唱后庭花</li>
	</ol>
	<div id="pp">
		<div>
			<a href="http://www.baidu.com">李白</a>
		</div>
		<ol>
			<li class="huanghe">君不见黄河之水天上来,奔流到海不复回</li>
			<li id="tata" class="hehe">李白乘舟将欲行,忽闻岸上踏歌声</li>
			<li class="tanshui">桃花潭水深千尺,不及汪伦送我情</li>
		</ol>
		<div class="hh">
			<a href="http://mi.com">雷军</a>
		</div>
		<ol>
			<li class="dudu">are you ok</li>
			<li class="meme">会飞的猪</li>
		</ol>
	</div>
</body>
</html>

联想一下,将html页面转化为节点树的模型在这里插入图片描述

3、xpath的相关语法

myxpath .py
该文件和html文件同级目录,如果不同级,需要修改下方的路径

from lxml import etree

# 1  将一个xml文件创建成一个树形结构

html_tree = etree.parse('./test.html')
print(html_tree)
# 得到结果是一个对象 <lxml.etree._ElementTree object at 0x0000013D7CF0DD88>
# 节点树


# 2 获取节点树上节点

# 用xpath路径在节点树上获取目标节点
ret = html_tree.xpath('/html/body/ol/li[1]')
#  '/' 代表当前目录的子目录(当前节点的子节点)  '//'代表当前节点的后代节点
# '[]' 代表对前面的节点进行条件修饰 [1]表示第一个
print(ret)

# 提取根节点的后代中所有的li节点
ret2 = html_tree.xpath('//li')
print(ret2)

# 查找页面上所有的带属性的li
ret3 = html_tree.xpath ('//li[@id]')
print(ret3)



# 3 提取内容和属性
#注意
#    1) 在xpath语法中所有的属性前面都要加上 @ 符号
#    2) xpath的属性修饰条件中,如果属性的取值有多个,一定要写全而且中间的间隔也要按照文件源码来写


# 提取节点的内容
ret4 = html_tree.xpath('/html/body/ol/li[3]/text()')
print(ret4)  #['一骑红尘妃子笑,无人知是荔枝来']

# 提取节点的属性
ret5 = html_tree.xpath('/html/body/div/div[1]/a/@href')
print(ret5)

#查找页面上所有的class值为li的内容
ret6 = html_tree.xpath('//li/text()')
print(ret6)

#查找页面上所有的class值为dudu的li的内容
ret6 = html_tree.xpath('//li[@class="dudu"]/text()')
print(ret6)   #['are you ok']

#查找页面上所有的div中的文本内容
ret7 = html_tree.xpath('//div//text()')
# 如果子节点中文本在提取的时候和上级节点重复,则不再提取
print(ret7)

# 查找页面上div属性中所有的后代节点id属性
ret8 = html_tree.xpath('//div//@id')
print(ret8)

#  4  模糊匹配

# 包含: 查找所有的class中包含h的li的文本
ret9 = html_tree.xpath('//li[contains(@class,"h")]/text()')
print(ret9)

# 开头: 查找所有的class值以h开头的li的文本
reta = html_tree.xpath('//li[starts-with(@class,"h")]/text()')
print(reta)

print('*****************')


# 5 逻辑匹配

# 与: 查找所有的既有id属性又有class属性的li的文本
ret_1 = html_tree.xpath("//li[@id and @class]/text()")

# 或: 查找所有的id值为hh或者class值为name的li的文本
ret_2 = html_tree.xpath("//li[@id='hh' or @class='meme']/text()")

print('*****************')

# 6 相对定位
# 以上的xpath路径都是从根节点开始查找的,这种路径为绝对路径
# 查找第二个ol
ol = html_tree.xpath("//ol[2]")[0]
# 以ol这个节点为基准向下查找

# 这样找到的其实是根节点下li的文本
ret_root = ol.xpath('//li/text()')
print(ret_root)
# 如果xpath路径中写的是绝对路径,根谁调xpath函数没有关系,查找的时候依然是从整个文件的根节点来查找

# 找ol节点下的li的文本
ret_revelative = ol.xpath('.//li//text()')
print(ret_revelative)
# "."代表当前路径相对路径,我们以哪个节点为基准(即用这个调用xpath函数),就会根据相对路径从这个节点向下查找
# ".."代表上一级路径,即以上一级路径为基准
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值