一、Beautiful Soup的簡介
簡單來說,Beautiful Soup是python的一個庫,最主要的功能是從網頁抓取數據。官方解釋如下:
Beautiful Soup提供一些簡單的、python式的函數用來處理導航、搜索、修改分析樹等功能。它是一個工具箱,通過解析文檔為用戶提供需要抓取的數據,因為簡單,所以不需要多少代碼就可以寫出一個完整的應用程序。
Beautiful Soup自動將輸入文檔轉換為Unicode編碼,輸出文檔轉換為utf-8編碼。你不需要考慮編碼方式,除非文檔沒有指定一個編碼方式,這時,Beautiful Soup就不能自動識別編碼方式了。然后,你僅僅需要說明一下原始編碼方式就可以了。
Beautiful Soup已成為和lxml、html6lib一樣出色的python解釋器,為用戶靈活地提供不同的解析策略或強勁的速度。
二、Beautiful Soup的下載與安裝
1 #安裝 Beautiful Soup 2 pip install beautifulsoup4 3 4 #安裝解析器 5 Beautiful Soup支持Python標准庫中的HTML解析器,還支持一些第三方的解析器,其中一個是 lxml .根據操作系統不同,可以選擇下列方法來安裝lxml: 6 7 $ apt-get install Python-lxml 8 9 $ easy_install lxml 10 11 $ pip install lxml 12 13 另一個可供選擇的解析器是純Python實現的 html5lib , html5lib的解析方式與瀏覽器相同,可以選擇下列方法來安裝html5lib: 14 15 $ apt-get install Python-html5lib 16 17 $ easy_install html5lib 18 19 $ pip install html5lib
三、 Beautiful Soup的簡單使用
1 ''' 2 pip3 install beautifulsoup4 # 安裝bs4 3 pip3 install lxml # 下載lxml解析器 4 ''' 5 html_doc = """ 6 <html><head><title>The Dormouse's story</title></head> 7 <body> 8 <p class="sister"><b>$37</b></p> 9 <p class="story" id="p">Once upon a time there were three little sisters; and their names were 10 <a href="http://example.com/elsie" class="sister" >Elsie</a>, 11 <a href="http://example.com/lacie" class="sister" id="link2">Lacie</a> and 12 <a href="http://example.com/tillie" class="sister" id="link3">Tillie</a>; 13 and they lived at the bottom of a well.</p> 14 15 <p class="story">...</p> 16 """ 17 18 # 從bs4中導入BeautifulSoup 19 from bs4 import BeautifulSoup 20 21 # 調用BeautifulSoup實例化得到一個soup對象 22 # 參數一: 解析文本 23 # 參數二: 24 # 參數二: 解析器(html.parser、lxml...) 25 soup = BeautifulSoup(html_doc, 'lxml') 26 27 print(soup) 28 print('*' * 100) 29 print(type(soup)) 30 print('*' * 100) 31 # 文檔美化 32 html = soup.prettify() 33 print(html)
四、 Beautiful Soup之遍歷文檔樹
1 html_doc = """ 2 <html><head><title>The Dormouse's story</title></head> 3 <body> 4 <p class="sister"><b>$37</b></p> 5 <p class="story" id="p">Once upon a time there were three little sisters; and their names were 6 <a href="http://example.com/elsie" class="sister" >Elsie</a>, 7 <a href="http://example.com/lacie" class="sister" id="link2">Lacie</a> and 8 <a href="http://example.com/tillie" class="sister" id="link3">Tillie</a>; 9 and they lived at the bottom of a well.</p> 10 11 <p class="story">...</p> 12 """ 13 from bs4 import BeautifulSoup 14 soup = BeautifulSoup(html_doc, 'lxml') 15 16 ''' 17 遍歷文檔樹: 18 1、直接使用 19 2、獲取標簽的名稱 20 3、獲取標簽的屬性 21 4、獲取標簽的內容 22 5、嵌套選擇 23 6、子節點、子孫節點 24 7、父節點、祖先節點 25 8、兄弟節點 26 ''' 27 28 # 1、直接使用 29 print(soup.p) # 查找第一個p標簽 30 print(soup.a) # 查找第一個a標簽 31 32 # 2、獲取標簽的名稱 33 print(soup.head.name) # 獲取head標簽的名稱 34 35 # 3、獲取標簽的屬性 36 print(soup.a.attrs) # 獲取a標簽中的所有屬性 37 print(soup.a.attrs['href']) # 獲取a標簽中的href屬性 38 39 # 4、獲取標簽的內容 40 print(soup.p.text) # $37 41 42 # 5、嵌套選擇 43 print(soup.html.head) 44 45 # 6、子節點、子孫節點 46 print(soup.body.children) # body所有子節點,返回的是迭代器對象 47 print(list(soup.body.children)) # 強轉成列表類型 48 49 print(soup.body.descendants) # 子孫節點 50 print(list(soup.body.descendants)) # 子孫節點 51 52 # 7、父節點、祖先節點 53 print(soup.p.parent) # 獲取p標簽的父親節點 54 # 返回的是生成器對象 55 print(soup.p.parents) # 獲取p標簽所有的祖先節點 56 print(list(soup.p.parents)) 57 58 # 8、兄弟節點 59 # 找下一個兄弟 60 print(soup.p.next_sibling) 61 # 找下面所有的兄弟,返回的是生成器 62 print(soup.p.next_siblings) 63 print(list(soup.p.next_siblings)) 64 65 # 找上一個兄弟 66 print(soup.a.previous_sibling) # 找到第一個a標簽的上一個兄弟節點 67 # 找到a標簽上面的所有兄弟節點 68 print(soup.a.previous_siblings) # 返回的是生成器 69 print(list(soup.a.previous_siblings))
四、 Beautiful Soup之搜索文檔樹
1 html_doc = """ 2 <html><head><title>The Dormouse's story</title></head> 3 <body> 4 <p class="sister"><b>$37</b></p> 5 <p class="story" id="p">Once upon a time there were three little sisters; and their names were 6 <a href="http://example.com/elsie" class="sister" >Elsie</a>, 7 <a href="http://example.com/lacie" class="sister" id="link2">Lacie</a> and 8 <a href="http://example.com/tillie" class="sister" id="link3">Tillie</a>; 9 and they lived at the bottom of a well.</p> 10 11 <p class="story">...</p> 12 """ 13 ''' 14 搜索文檔樹: 15 find() 找一個 16 find_all() 找多個 17 18 標簽查找與屬性查找: 19 標簽: 20 name 屬性匹配 21 attrs 屬性查找匹配 22 text 文本匹配 23 24 - 字符串過濾器 25 字符串全局匹配 26 27 - 正則過濾器 28 re模塊匹配 29 30 - 列表過濾器 31 列表內的數據匹配 32 33 - bool過濾器 34 True匹配 35 36 - 方法過濾器 37 用於一些要的屬性以及不需要的屬性查找。 38 39 屬性: 40 - class_ 41 - id 42 ''' 43 44 from bs4 import BeautifulSoup 45 soup = BeautifulSoup(html_doc, 'lxml') 46 47 # # 字符串過濾器 48 # name 49 p_tag = soup.find(name='p') 50 print(p_tag) # 根據文本p查找某個標簽 51 # # 找到所有標簽名為p的節點 52 tag_s1 = soup.find_all(name='p') 53 print(tag_s1) 54 # 55 # 56 # # attrs 57 # # 查找第一個class為sister的節點 58 p = soup.find(attrs={"class": "sister"}) 59 # print(p) 60 # # 查找所有class為sister的節點 61 tag_s2 = soup.find_all(attrs={"class": "sister"}) 62 print(tag_s2) 63 64 65 # text 66 text = soup.find(text="$37") 67 print(text) 68 # 69 # 70 # # 配合使用: 71 # # 找到一個id為link2、文本為Lacie的a標簽 72 a_tag = soup.find(name="a", attrs={"id": "link2"}, text="Lacie") 73 print(a_tag) 74 75 76 77 # # 正則過濾器 78 import re 79 # name 80 p_tag = soup.find(name=re.compile('p')) 81 print(p_tag) 82 83 # 列表過濾器 84 import re 85 # name 86 tags = soup.find_all(name=['p', 'a', re.compile('html')]) 87 print(tags) 88 89 # - bool過濾器 90 # True匹配 91 # 找到有id的p標簽 92 p = soup.find(name='p', attrs={"id": True}) 93 print(p) 94 95 # 方法過濾器 96 # 匹配標簽名為a、屬性有id沒有class的標簽 97 def have_id_class(tag): 98 if tag.name == 'a' and tag.has_attr('id') and tag.has_attr('class'): 99 return tag 100 101 tag = soup.find(name=have_id_class) 102 print(tag)
