lxml:python 的HTML/XML的解析器
lxml是Python中一个非常强大的XML和HTML处理库。它是基于C语言的libxml2库进行开发的,具有高性能和高效的特点,适用于解析和操作大型XML和HTML文档。
lxml库提供了一些非常方便的功能,包括:
- 解析XML和HTML文档:lxml可以将XML和HTML文档解析为树状结构,以便于对文档进行操作和查询。
- 定位元素:lxml支持使用XPath和CSS选择器来定位文档中的元素,从而方便地提取出所需的数据。
- 修改文档:lxml可以方便地对文档进行修改、添加、删除等操作,比如修改元素的属性或文本内容。
- 序列化和反序列化:lxml可以将解析后的文档序列化为字符串或写入文件,也可以将字符串反序列化为文档对象。
- 命名空间处理:lxml可以处理包含命名空间的XML文档,并提供了方便的方式来处理命名空间。
使用lxml库需要先安装lxml模块,在Python中可以使用pip命令进行安装:
pip install lxml
下面是一个使用lxml库解析XML文档的示例代码:
from lxml import etree
# 解析XML文档
doc = etree.parse('example.xml')
# 使用XPath定位元素
elements = doc.xpath('//book')
# 输出元素内容
for element in elements:
print(element.text)
以上代码首先导入了lxml库中的etree模块,然后使用etree模块的parse方法解析了一个名为example.xml的XML文档,接着使用XPath定位到了所有的book元素,并输出了其内容。
除了解析XML文档,lxml还可以用于解析和修改HTML文档,具体的使用方法可以参考lxml官方文档。
etree模块
etree模块是Python中的一个XML处理模块,可以用于解析和操作XML文档。
该模块提供了ElementTree类,该类是一个对象模型,可以表示XML文档中的元素和它们之间的关系。通过使用ElementTree类的方法,可以轻松地遍历、搜索和修改XML文档。一些常用的方法包括:
etree.parse(filename) | 从文件中解析XML文档并返回一个ElementTree对象。 |
etree.fromstring(xmlstring) | 从字符串中解析XML文档并返回一个ElementTree对象。 |
etree.Element(tagname) | 创建一个具有给定标签名的元素。 |
element.find(xpath) | 从给定元素中查找第一个匹配给定XPath表达式的子元素,并返回该元素。 |
element.findall(xpath) | 从给定元素中查找所有匹配给定XPath表达式的子元素,并返回一个列表。 |
element.text | 获取或设置给定元素的文本内容。 |
element.attrib | 获取或设置给定元素的属性。 |
除了ElementTree类,etree模块还提供了其他一些类和方法,用于处理XML文档,例如Element类、ElementPath类和ElementTree类等。
要使用etree模块,需要先安装lxml库。可以通过在命令行中运行pip install lxml
命令来安装lxml库。
下面是一个使用etree模块的例子,假设有一个名为example.xml的XML文档:
from lxml import etree
# 解析XML文档
tree = etree.parse('example.xml')
# 获取根元素
root = tree.getroot()
# 遍历所有的book元素
for book in root.findall('book'):
# 获取title元素的文本内容
title = book.find('title').text
print(title)
这个例子解析了example.xml文档,并遍历了所有的book元素,然后获取了每个book元素的title元素的文本内容并进行了打印。
应用案例
对网站的首页包括每一个分页的图片进行爬取
首先,导入需要的request,etree,os的模块,以及指定爬取的网址和请求头
import requests
from lxml import etree
import os
if __name__=="__main__":
url="https://pic.netbian.com/4kyouxi"
headers = {
'User-Agent': "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Mobile Safari/537.36 Edg/122.0.0.0"
}
再通过requests.get().content获取网站首页的HTML数据,F12观察使用xpath定位多个li标签
page_text=requests.get(url=url,headers=headers).content
tree=etree.HTML(page_text)
h3_list=tree.xpath('//*[@id="main"]/div[3]/ul/li')
从上边xpath会返回一个li标签的列表,再用一个循环,然后我们能够单独对每一张图片进行处理,
@src可以获取图片的属性的值,因为xpath返回的是一个列表,所以可以用【0】来获取其中的值
text()可以获取标签中的文本内容,借此作为图片的名字,利用os创建的目录来保存每次爬取的图片
if not os.path.exists('./4kLibs'):
os.mkdir('./4kLibs')
for a_text in h3_list:
img_src="https://pic.netbian.com/"+a_text.xpath('./a/img/@src')[0]
img_name=a_text.xpath('./a/b/text()')[0]+'.jpg'
img_data=requests.get(url=img_src,headers=headers).content
img_path='./4kLibs/'+img_name
with open(img_path,'wb')as fp:
fp.write(img_data)
print(img_name+'下载成功!')
最后,为实现分页的中所包含的图片进行爬取,我先可以对其网站的url观察一下
发现网站首页和第2页的url的区别在有一个index_2html
而且第3页的内容为index_3html,默认首页是没有这index_页码html的,那么我们就可以进行一个判断,如果它的url不是第一页就加上index.数字html嘛,循环多少次我们以上的步骤就是获取多少分页的全部图片
for ur in range(1,3):
if ur>1:
url = url + '/index_' + str(ur) + '.html'
完整代码
import requests
from lxml import etree
import os
if __name__=="__main__":
url="https://pic.netbian.com/4kyouxi"
headers = {
'User-Agent': "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Mobile Safari/537.36 Edg/122.0.0.0"
}
for ur in range(1,3):
if ur>1:
url = url + '/index_' + str(ur) + '.html'
page_text=requests.get(url=url,headers=headers).content
tree=etree.HTML(page_text)
h3_list=tree.xpath('//*[@id="main"]/div[3]/ul/li')
if not os.path.exists('./4kLibs'):
os.mkdir('./4kLibs')
for a_text in h3_list:
img_src="https://pic.netbian.com/"+a_text.xpath('./a/img/@src')[0]
img_name=a_text.xpath('./a/b/text()')[0]+'.jpg'
img_data=requests.get(url=img_src,headers=headers).content
img_path='./4kLibs/'+img_name
with open(img_path,'wb')as fp:
fp.write(img_data)
print(img_name+'下载成功!')
点击运行就可以获取每一个分页的内容啦