BeautifulSoup和etree的區別和使用場景
建立時間:2024年3月5日
BeautifulSoup
和 etree
都是用於解析HTML和XML文件的工具,但它們有一些不同之處,適用於不同的使用場景。以下是它們的主要區別和一些使用場景:
BeautifulSoup:
- 靈活而簡單:
BeautifulSoup
提供了一種簡單而靈活的方式來瀏覽、搜尋和修改HTML/XML文件的樹結構。- 主要用於提取和解析HTML內容,對HTML標籤的操作非常直觀。
- 解析器多樣性:
BeautifulSoup
支援多種解析器,如 Python 標準庫中的html.parser
,以及第三方的解析器如lxml
和html5lib
。- 解析器的選擇取決於效能需求和HTML文件的特性。
- 處理糟糕的HTML:
BeautifulSoup
能夠處理糟糕的、不規範的HTML,具有一定的容錯性。
- 適用於初學者:
- 適用於初學者和快速開發,提供了易於使用的API。
etree (ElementTree):
- 更高效的解析:
etree
是lxml
庫的一部分,相對於BeautifulSoup
在解析效能上更為高效。lxml
使用了C語言編寫,因此通常比純Python實現的解析器更快。
- XPath支援:
etree
支援XPath表示式,可以方便地使用XPath語法來定位和選擇XML/HTML文件中的元素。- 對於複雜的文件結構或需要精準定位的情況,XPath是一種強大的選擇。
- 更底層的控制:
etree
提供了更底層的控制,可以更靈活地操作XML文件。- 如果需要更多的控制和直接訪問XML節點,
etree
可能更適合。
- 較小的記憶體佔用:
lxml
的etree
通常佔用較小的記憶體,適用於處理大型文件。
使用場景:
- 使用 BeautifulSoup 的場景:
- 當你主要關注HTML的易讀性和可操作性,而不太關心效能。
- 當你處理糟糕、不規範的HTML文件時。
- 當你是初學者,希望使用簡單而直觀的API進行HTML解析。
- 使用 etree 的場景:
- 當你需要更高效的效能,特別是在處理大型文件時。
- 當你需要使用XPath表示式來進行精確的元素選擇和定位。
- 當你希望在解析XML文件時獲得更底層的控制。
使用的完整程式碼
import requests
from bs4 import BeautifulSoup
from lxml import etree
url = 'http://www.netbian.com/keai/'
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/113.0.0.0 Safari/537.36 Edg/113.0.1774.35'}
# response = requests.request("get", url=url, headers=headers)
# html = response.content.decode('gbk', errors='ignore') # 使用GBK解碼,並忽略錯誤
# soup = BeautifulSoup(html, "lxml")
# # print(soup)
# for i in soup.find_all(attrs={"class": "list"}):
# # print(i)
# for o in i.find_all("img"):
# # print(o)
# print(o.get('src'))
#
resp = requests.get(url, headers=headers)
resp.encoding = resp.apparent_encoding
# 將響應內容解析為etree物件
xp = etree.HTML(resp.text)
# print(type(xp))
# 獲取每頁中的圖片詳情頁連結
# img_url = xp.xpath("/html/body/div[@class='wrap clearfix']/div[@id='main']/div[@class='list']/ul/li/a/img/@src")
img_url = xp.xpath("//div[@class='list']/ul/li/a/img/@src")
print(img_url)
使用的案例
針對一個網站
http://www.netbian.com/keai/
假設我們需要抓取下面的src
需要抓取的資料:
先使用BeautifulSoup進行載入頁面:
url = 'http://www.netbian.com/keai/'
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/113.0.0.0 Safari/537.36 Edg/113.0.1774.35'}
response = requests.request("get", url=url, headers=headers)
html = response.content.decode('gbk', errors='ignore') # 使用GBK解碼,並忽略錯誤
soup = BeautifulSoup(html, "lxml")
print(soup)
處理我們需要的資料
# print(soup)
for i in soup.find_all(attrs={"class": "list"}):
# print(i)
for o in i.find_all("img"):
# print(o)
print(o.get('src'))
使用我們的etree 進行載入頁面
resp = requests.get(url, headers=headers)
resp.encoding = resp.apparent_encoding
# 將響應內容解析為etree物件
xp = etree.HTML(resp.text)
是一個類。我們可以按照xpath進行提取資料
img_url = xp.xpath("/html/body/div[@class='wrap clearfix']/div[@id='main']/div[@class='list']/ul/li/a/img/@src")
print(img_url)
或者
img_url = xp.xpath("//div[@class='list']/ul/li/a/img/@src")
print(img_url)
結論:
在我看來,對比兩者,使用etree
確實更為簡潔。然而,etree
需要額外學習XPath表示式,這可能會增加一些學習成本。另一方面,BeautifulSoup返回的是HTML結構物件,這使其更適合於定位和提取所需內容。因此,大多數教學資料都傾向於使用BeautifulSoup。不過,對於有興趣深入學習的同學來說,嘗試將之前的抓取程式修改為使用etree
將是一個很好的實踐機會。畢竟,學無止境,不斷挑戰和嘗試新的方法和技術,將有助於我們不斷提升自己的技能水平。
學習資料:
beautifulsoup
https://beautifulsoup.cn/
etree
https://docs.python.org/3/library/xml.etree.elementtree.html
https://www.runoob.com/xpath/xpath-tutorial.html