python範例詳解之xpath解析

2022-03-31 13:00:08
本篇文章給大家帶來了關於的相關知識,其中主要介紹了xpath的相關問題,XPath,全稱XML Path Language,即XML路徑語言,它是一門在XML檔案中查詢資訊的語言,希望對大家有幫助。

推薦學習:

XPath,全稱XML Path Language,即XML路徑語言,它是一門在XML檔案中查詢資訊的語言,它最初是用來搜尋XML檔案的,但是它同樣適用於HTML檔案的搜尋

XPath的選擇功能十分強大,它提供了非常簡明的路徑選擇表示式,另外,它還提供了超過100個內建函數,用於字串、數值、時間的匹配以及節點、序列的處理等,幾乎所有我們想要定位的節點,都可以用XPath來選擇

xpath解析原理:

  • 實現標籤的定位:範例化一個etree的物件,且需要將被解析的頁面原始碼資料載入到該物件中。

  • 呼叫etree物件中的xpath方法結合著xpath表示式實現標籤的定位和內容的捕獲。

環境的安裝

pip install lxml

lxml是python的一個解析庫,支援HTML和XML的解析,支援XPath解析方式,而且解析效率非常高

如何範例化一個etree物件

1.將原生的html檔案中的原始碼資料載入到etree物件中:

etree. parse(filePath)#你的檔案路徑

2.可以將從網際網路上獲取的原始碼資料載入到該物件中

etree.HtML('page_ text')#page_ text網際網路中響應的資料

xpath 表示式

表示式描述
nodename選取此節點的所有子節點
/表示的是從根節點開始定位。表示的是一個層級。
//表示的是多個層級。可以表示從任意位置開始定位。
.選取當前節點
選取當前節點的父節點
@選取屬性
*萬用字元,選擇所有元素節點與元素名
@*選取所有屬性
[@attrib]選取具有給定屬性的所有元素
[@attrib=‘value’]選取給定屬性具有給定值的所有元素
[tag]選取所有具有指定元素的直接子節點
[tag=‘text’]選取所有具有指定元素並且文字內容是text節點

對上面表示式的範例詳解

這是一個HTML的檔案

<html lang="en"><head>
	<meta charset="UTF-8" />
	<title>測試bs4</title></head><body>
	<p>
		<p>百里守約</p>
	</p>
	<p class="song">
		<p>李清照</p>
		<p>王安石</p>
		<p>蘇軾</p>
		<p>柳宗元</p>
		<a href="http://www.song.com/" title="趙匡胤" target="_self">
			<span>this is span</span>
		宋朝是最強大的王朝,不是軍隊的強大,而是經濟很強大,國民都很有錢</a>
		<a href="" class="du">總為浮雲能蔽日,長安不見使人愁</a>
		<img src="http://www.baidu.com/meinv.jpg" alt="" />
	</p>
	<p class="tang">
		<ul>
			<li><a href="http://www.baidu.com" title="qing">清明時節雨紛紛,路上行人慾斷魂,借問酒家何處有,牧童遙指杏花村</a></li>
			<li><a href="http://www.163.com" title="qin">秦時明月漢時關,萬里長征人未還,但使龍城飛將在,不教胡馬度陰山</a></li>
			<li><a href="http://www.126.com" alt="qi">岐王宅裡尋常見,崔九堂前幾度聞,正是江南好風景,落花時節又逢君</a></li>
			<li><a href="http://www.sina.com" class="du">杜甫</a></li>
			<li><a href="http://www.dudu.com" class="du">杜牧</a></li>
			<li><b>杜小月</b></li>
			<li><i>度蜜月</i></li>
			<li><a href="http://www.haha.com" id="feng">鳳凰臺上鳳凰遊,鳳去臺空江自流,吳宮花草埋幽徑,晉代衣冠成古丘</a></li>
		</ul>
	</p></body></html>

從瀏覽器中開啟是這樣的
在這裡插入圖片描述
為了方便直觀,我們對寫個HTML檔案進行本地讀取進行測試

子節點和子孫節點的定位 / 和 //

先來看子節點和子孫節點,我們從上往下找p這個節點,可以看到p的父節點是body,body父節點是html
在這裡插入圖片描述
定位到這個HTML的p物件中,看上面html原始碼,可以知道有三個p物件
在這裡插入圖片描述在這裡插入圖片描述在這裡插入圖片描述
我們通過三種不同的方法來輸出這個節點的資訊,可以看到輸出的是三個一樣的Element,也就是這三種方法實現的功能是一樣的。

import requestsfrom lxml import etree
tree = etree.parse('test.html')r1=tree.xpath('/html/body/p')	#直接從上往下挨著找節點r2=tree.xpath('/html//p')#跳躍了一個節點來找到這個p節點的物件r3=tree.xpath('//p')##跳躍上面所有節點來尋找p節點的物件r1,r2,r3>>([<Element p at 0x19d44765108>,
  <Element p at 0x19d447658c8>,
  <Element p at 0x19d44765588>],
  
 [<Element p at 0x19d44765108>,
  <Element p at 0x19d447658c8>,
  <Element p at 0x19d44765588>],
  
 [<Element p at 0x19d44765108>,
  <Element p at 0x19d447658c8>,
  <Element p at 0x19d44765588>])

屬性定位

如果我只想要p裡面song這一個標籤,就可以對其屬性定位
在這裡插入圖片描述
當然返回的還是一個element

r4=tree.xpath('//p[@class="song"]')r4>>>[<Element p at 0x19d447658c8>]

索引定位

如果我只想獲得song裡面的蘇軾的這個標籤
我們找到了song,/p可以返回裡面的所有標籤,

tree.xpath('//p[@class="song"]/p')>>[<Element p at 0x19d4469a648>,
 <Element p at 0x19d4469a4c8>,
 <Element p at 0x19d4469af88>,
 <Element p at 0x19d4469a148>]

這個單獨返回的蘇軾的p標籤,要注意的是這裡的索引不是從0開始的,而是1

tree.xpath('//p[@class="song"]/p[3]')[<Element p at 0x19d4469af88>]

取文字

比如我想取杜牧這個文字內容
在這裡插入圖片描述
和上面一樣,我們要定位到杜牧的這個a標籤,首先要找到他的上一級 li ,這是第五個 li 裡面的a所以就有了下面的寫法,text()是把element轉化為文字,當然上面的在後面加個text()都可以展示文字內容。

tree.xpath('//p[@class="tang"]//li[5]/a/text()')>>['杜牧']

可以看到這個返回的是一個列表,如果我們想取裡面的字串,可以這樣

tree.xpath('//p[@class="tang"]//li[5]/a/text()')[0]杜牧

看一個更直接的,//li 直接定位到 li這個標籤,//text()直接將這個標籤下的文字提取出來。但要注意,這樣會把所有的li標籤下面的文字提取出來,有時候你並不想要的文字也會提取出來,所以最好還是寫詳細一點,如具體到哪個p裡的li。

tree.xpath('//li//text()')['清明時節雨紛紛,路上行人慾斷魂,借問酒家何處有,牧童遙指杏花村',
 '秦時明月漢時關,萬里長征人未還,但使龍城飛將在,不教胡馬度陰山',
 '岐王宅裡尋常見,崔九堂前幾度聞,正是江南好風景,落花時節又逢君',
 '杜甫',
 '杜牧',
 '杜小月',
 '度蜜月',
 '鳳凰臺上鳳凰遊,鳳去臺空江自流,吳宮花草埋幽徑,晉代衣冠成古丘']

取屬性

比如我想取下面這個屬性
在這裡插入圖片描述
可以直接用@取屬性

tree.xpath('//p[@class="song"]/img/@src')['http://www.baidu.com/meinv.jpg']

或者如果我想取所有的href這個屬性,可以看到tang和song的所有href屬性

tree.xpath('//@href')['http://www.song.com/',
 '',
 'http://www.baidu.com',
 'http://www.163.com',
 'http://www.126.com',
 'http://www.sina.com',
 'http://www.dudu.com',
 'http://www.haha.com']

爬蟲實戰之58同城房源資訊

#匯入必要的庫import requestsfrom lxml import etree#URL就是網址,headers看圖一url='https://sh.58.com/ershoufang/'headers={'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.7 Safari/537.36'}#對網站發起請求page_test=requests.get(url=url,headers=headers).text# 這裡是將從網際網路上獲取的原始碼資料載入到該物件中tree=etree.HTML(page_test)#先看圖二的解釋,這裡li有多個,所裡返回的li_list是一個列表li_list=tree.xpath('//ul[@class="house-list-wrap"]/li')#這裡我們開啟一個58.txt檔案來儲存我們的資訊fp=open('58.txt','w',encoding='utf-8')#li遍歷li_listfor li in li_list:
	#這裡 ./是對前面li的繼承,相當於li/p...
    title=li.xpath('./p[2]/h2/a/text()')[0]
    print(title+'\n')
    #把檔案寫入檔案
    fp.write(title+'\n')fp.close()

圖一:
在這裡插入圖片描述
圖二:.
這裡我們要提取所有的房源資訊,可以看到每個小節點的上一個節點都是一樣的,我們要提取的是h2節點a裡的房源資訊,看圖三
在這裡插入圖片描述
這裡每個 /li 節點裡面的子節點都是一樣的,所以我們可以先找到所有的li節點,再往下找我們想要的資訊

在這裡插入圖片描述

推薦學習:

以上就是python範例詳解之xpath解析的詳細內容,更多請關注TW511.COM其它相關文章!