什么是 Xpath?
XPath 即為 XML 路徑語言,它是一種用來確定 XML (標(biāo)準(zhǔn)通用標(biāo)記語言子集)文檔中某部分位置的語言。XPath 基于 XML 的樹狀結(jié)構(gòu),提供在數(shù)據(jù)結(jié)構(gòu)樹中找尋節(jié)點的能力。起初 XPath 的提出的初衷是將其作為一個通用的、介于 XPointer 與 XSL 間的語法模型。但是 XPath 很快的被開發(fā)者采用來當(dāng)作小型查詢語言。
簡單的來說:Xpath(XML Path Language)是一門在 XML 和 HTML 文檔中查找信息的語言,可用來在 XML 和 HTML 文檔中對元素和屬性進行遍歷。
XPath 開發(fā)工具
這里給大家介紹兩個小編用得較多也是用得最為廣泛與便捷的工具:
- Chrome 插件 XPath Helper (需科學(xué)上網(wǎng));
- Firefox 插件 Try XPath。
當(dāng)然 Chrome 插件 XPath Helper 也可以尋找安裝包后通過插件伴侶安裝,安裝方法步驟如下:
- 打開插件伴侶,選擇下載好的插件;
- 選擇提取插件內(nèi)容到桌面,桌面上會多一個文件夾;
- 把文件夾放入想要放的路徑下;
- 打開谷歌瀏覽器,選擇擴展程序,開發(fā)者模式打開,選擇加載已解壓的擴展程序,選擇路徑打開即可。
XPath 節(jié)點
在 XPath 中,有七種類型的節(jié)點:元素、屬性、文本、命名空間、處理指令、注釋以及文檔(根)節(jié)點。XML 文檔是被作為節(jié)點樹來對待的。樹的根被稱為文檔節(jié)點或者根節(jié)點。
XPath 語法
XPath 使用路徑表達式來選取 XML 文檔中的節(jié)點或節(jié)點集。節(jié)點是通過沿著路徑 (path) 或者步 (steps) 來選取的。
使用方式:
使用 // 獲取整個頁面當(dāng)中的元素,然后寫標(biāo)簽名,然后在寫謂語進行提取,比如:
//title[@lang='en']
需要注意的知識點:
- / 和 // 的區(qū)別:/ 代表只獲取子節(jié)點,// 獲取子孫節(jié)點,一般 // 用的比較多,當(dāng)然也要視情況而定;
- contains:有時候某個屬性中包含了多個值,那么可以使用 contains 函數(shù),示例如下:
//title[contains(@lang,'en')]
- 謂詞中下標(biāo)是從 1 開始的,不是從 0 開始的
lxml 庫
lxml 是 一個HTML/XML的解析器,主要的功能是如何解析和提取 HTML/XML 數(shù)據(jù)。
該庫為第三方庫需使用 pip 進行安裝,命令如下:
pip install lxml
基本使用:
如下是案例實操的 html 文件代碼,屏幕前的小伙伴可以保存下來一起動手練習(xí)。
<div>
<ul>
<li class="im-0"><a href="link1.html"> first </a></li>
<li class="im-1"><a href="link2.html"> second </a></li>
<li class="im-active"><a href="link3.html"> third </a></li>
<li class="im-1"><a href="link4.html"> fourth </a></li>
<li class="im-0"><a href="link5.html"> fifth </a>
</ul>
</div>
案例 1:將字符串解析為 html 文檔
from lxml import etree
text = ''
html = etree.HTML(text) #讀取
print(html)
# 按字符串序列化html
result = etree.tostring(html).decode('utf-8')
print(result)
案例 2:從文件中讀取 html 代碼:
from lxml import etree
html = etree.parse('hello.html') #讀取
# 按字符串序列化html
result = etree.tostring(html).decode('utf-8')
print(result)
案例 3:在 lxml 中使用 Xpath 語法
from lxml import etree
html = etree.parse('hello.html')
# 獲取所有 li 標(biāo)簽:
# result = html.xpath('//li')
# print(result)
# for i in result:
# print(etree.tostring(i))
# 獲取所有l(wèi)i元素下的所有 class 屬性的值:
# result = html.xpath('//li/@class')
# print(result)
# 獲取 li 標(biāo)簽下 href 為http://m.hgci.cn/的 a 標(biāo)簽:
# result = html.xpath('//li/a[@href="http://m.hgci.cn/"]')
# print(result)
# 獲取 li 標(biāo)簽下所有 span 標(biāo)簽:
# result = html.xpath('//li//span')
# print(result)
# 獲取 li 標(biāo)簽下的 a 標(biāo)簽里的所有 class:
# result = html.xpath('//li/a//@class')
# print(result)
# 獲取最后一個 li 的 a 的 href 屬性對應(yīng)的值:
# result = html.xpath('//li[last()]/a/@href')
# print(result)
# 獲取倒數(shù)第二個 li 元素的內(nèi)容:
# result = html.xpath('//li[last()-1]/a')
# print(result)
# print(result[0].text)
# 獲取倒數(shù)第二個 li 元素的內(nèi)容的第二種方式:
result = html.xpath('//li[last()-1]/a/text()')
print(result)
總結(jié):
紙上得來終覺淺,絕知此事要躬行,一份耕耘,一份收獲。
推薦好課:Python 靜態(tài)爬蟲、Python Scrapy網(wǎng)絡(luò)爬蟲。