python爬蟲三大解析庫之XPath解析庫通俗易懂詳講


@

使用XPath解析庫

1.簡介

  XPath(全稱XML Path Languang),即XML路徑語言,是一種在XML文檔中查找信息的語言。適用於XML和HTML文檔的搜索。
  優點:提供了非常簡潔明了的路徑選擇表達式。還提供了超過100個內建函數,可以匹配大部分的節點。
  官網:https://www.w3.org/TR/xpath/
  准備工作:需要安裝lxml庫。

2.常用規則

表達式 功能
nodename 選取此節點的所有子節點
/ 從當前節點選取直接子節點
// 從當前節點選取直接子孫節點
. 選取當前節點
.. 選取當前節點的父節點
@ 選取屬性

3.etree模塊解析網頁簡介

  etree是lxml庫中的函數,可以自動修正HTML文本。下面是兩種導入方法:
  直接讀取網頁代碼進行解析:

from lxml import etree
text = '''
HTML文本
'''
# 將HTML文本轉化為可以用etree解析的對象,
html = etree.HTML(text)	# 結果是bytes類型,如果需要文本輸出,則需要用decode()轉碼為Unicode編碼

  讀取文本文件進行解析(這里既會自動修正文件,又會補充DOCTYPE聲明):

from lxml import etree
html = etree.parse('文本文件路徑/文本文件名字.html',etree.HTMLParse()) # 結果是bytes類型,如果需要文本輸出,則需要用decode()轉碼為Unicode編碼

  用tostring()方法即可輸出修正后的HTML代碼。

4.選取所有節點,子節點和父節點

(1)選取所有節點

  一般用//開頭的XPath規則,就會選擇從當前節點開始的所有子孫節點,也就是所有節點。所以要匹配所有的節點代碼如下:

a = html.xpath('//*')	# 選取所有的節點
b = html.xpath('//a')	# 選取所有的a節點,是一個例子

  這里的a和b,也就是xpath方法的返回值是一個列表,每個元素是Element類型,后面跟着節點的名稱,是一個可迭代對象。要取出某一個對象,就需要用處理列表的方法進行。

(2)選取子節點

  選取子節點只需要在后面加上/節點名稱(選擇直接子節點,也就是與其相鄰的第一個子節點),如果直接子節點沒有就會報錯,或者//節點名稱(選擇所有子孫節點),例子如下:

c = html.xpath('//li/a')	# 選取li節點的直接a子節點
d = html.xpath('//li//a')	# 選取li節點的所有a子節點
(3)選取父節點

  獲取某個節點的父節點有兩個方法,一個是用..,另一個是用parent::。
同理,如果沒有父節點,就會報錯,例子如下:

e = html.xpath('//li/../a')	# 選取li節點的父節點下的a節點
f = html.xpath('//li/parent::/a')	# 選取li節點的父節點下的直接a節點
g = html.xpath('//li/parent::*/a')	# 選取li節點的父節點下的所有a節點

5.屬性匹配,文本獲取和屬性多值匹配

(1)屬性匹配

  在選取節點的時候,可以用@符號進行屬性過濾,用[@屬性名="屬性值"]進行實現,例子如下:

s = html.xpath('//li[@class="ming"]')	# 選取屬性值class="ming"的所有li節點

  要注意的是里面的括號和外面的括號盡量一個用雙引號,一個用單引號。

(2)文本獲取

  我們用Xpath中的text()方法即可獲取節點中的文本。要注意的是獲取到的數據可能包括換行符'\n'。

(3)屬性多值匹配

  要是屬性有多個值的話,用上面的方法就無法匹配了。需要用到contains()函數,包含兩個參數,即@屬性名和屬性值,例子如下:

# 源代碼中為<li class="ming1 ming2">
s1 = html.xpath('//li[contains(@class,"ming1")]')	# 選取屬性值class="ming1"的所有li節點
s2 = html.xpath('//li[contains(@class,"ming2")]')	# 選取屬性值class="ming2"的所有li節點

6.屬性獲取和多屬性匹配

(1)屬性獲取

  屬性獲取直接用@獲取即可,例子如下:

s = html.xpath('//li/a/@href]')	# 獲取所有li節點下的直接a子節點的href屬性
(2)多屬性匹配

  有時候需要根據多個屬性值確定一個節點,就需要同時匹配多個屬性。要用and進行連接,可以把contains(@屬性名,"屬性名")和@屬性名="屬性值"混合使用,例子如下:

# 選取所有屬性值class="a"和_target="ming"的li節點下的所有a節點的href屬性
two_s = html.xpath('//li[contains(@class,"a") and @_target="ming"]//a/@href')

7.按次序選擇

  有時候選擇到的某些屬性可能同時匹配了多個節點,但是要想得到其中的某一個節點,該如何獲取呢?可以用中括號傳入索引的方法獲取特定次序的節點。下面是一些常用方法的總結:

方法 功能
[n] 選取第n個節點,序號是以1開頭的
[last()] 選取最后一個節點
[position() < n] 選取位置小於n的節點,這里可以用算術運算符進行選擇
[last() - n] 選取倒數第n+1個節點,由於last()是倒數第一個,則last() - n就是倒數第n+1個

8.節點軸選擇

  由於網頁代碼是一個DOM樹,因此可以用相對的位置進行選擇節點的子節點,兄弟節點,父節點或者祖先節點等。python的節點軸選擇常用的如下:

節點軸 選擇節點
ancestor:: * 獲取所有祖先節點
ancestor::條件 獲取指定條件的祖先節點
attribute:: * 獲取節點的所有屬性
attribute::屬性名 獲取節點的指定屬性
child:: * 獲取所有子節點
child::條件 獲取指定條件的子節點
descendent:: * 獲取所有的子孫節點
descendent::條件 獲取指定條件的子孫節點
following:: * 獲取當前節點之后的所有節點
following:: *[n] 獲取當前節點之后的第n個節點
following-sibing:: * 獲取當前節點之后的所有同級節點
following-sibing::條件 獲取當前節點之后指定條件的所有同級節點

9.開發者工具查看xpath選擇器路徑

  用F12打開開發者工具,按才Copy->Copy Xpath就可以把該段代碼的XPath路徑代碼復制下來,很方便。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM