Python數據采集-開始爬蟲
一 遍歷單個域名
網頁爬蟲,就是對目標網頁進行捉取,然後遍歷到數據信息,然後有鏈接的繼續遍歷,如此回調。
第一步:將頁面的所有鏈接獲取
1 from urllib.request import urlopen 2 from bs4 import BeautifulSoup 3 import re 4 5 html = urlopen("https://www.yahoo.com/") 6 html_str = html.read().decode(‘utf-8‘) 7 #print(html_str) 8 bsObj = BeautifulSoup(html_str) 9 ##獲取頁面鏈接地址 10 for link in bsObj.findAll("a"): 11 if ‘href‘ in link.attrs: 12 print(link.attrs[‘href‘])
運行效果圖
發現會存在些沒用用的數據,有些href的值只是作為頁面塊的跳轉,我們可以使用正則表達式進行優化過濾掉,只獲取帶有HTML結尾的鏈接
1 from urllib.request import urlopen 2 from bs4 import BeautifulSoup 3 import re 4 5 html = urlopen("https://www.yahoo.com/") 6 html_str = html.read().decode(‘utf-8‘) 7 #print(html_str) 8 bsObj = BeautifulSoup(html_str) 9 ##獲取頁面鏈接地址 10 for link in bsObj.findAll("a" ,href= re.compile(".*\.html")): 11 if ‘href‘ in link.attrs: 12 print(link.attrs[‘href‘])
第二步:遞歸獲取網頁
第一步我們基本把一個網頁的所有鏈接地址獲取到,第二步顯然是獲取這些鏈接網頁的鏈接,進一步獲取這些網頁數據。
例如我們在Wiki獲取Python詞條下面的相關詞條的鏈接,由於存在不是我們關心的鏈接,所有需要正則表達式過濾掉一部分,然後大量的鏈接的鏈接的鏈接,我們不可能窮盡,所有隨機獲取一些詞條。
1 from urllib.request import urlopen 2 from bs4 import BeautifulSoup 3 import re 4 import datetime 5 import random 6 7 rd = random.seed(datetime.datetime.now()) 8 print(rd) 9 10 def getLinks(articleUrl): 11 html = urlopen("https://en.wikipedia.org"+articleUrl) 12 bsObj = BeautifulSoup(html,"lxml") 13 return bsObj.findAll("a",href=re.compile("^(/wiki/)((?!:).)*$")) 14 15 links = getLinks("/wiki/Python") 16 17 while len(links) >0 : 18 #print(links) 19 newArticle = links[random.randint(0, len(links)-1)].attrs["href"]#隨機獲取一個來繼續爬 20 print(newArticle) 21 links = getLinks(newArticle)
運行結果(一分鐘150條數據產生,如非手動停止應該不會停止爬取)
二 采集整個網站
對整個站點進行所有鏈路采集,當然像wiki這些大型網站數據很多,要全部采集基本不可能。
1 from urllib.request import urlopen 2 from bs4 import BeautifulSoup 3 import re 4 pages = set() 5 def getLinks(pageUrl): 6 global pages 7 html = urlopen("http://en.wikipedia.org"+pageUrl) 8 bsObj = BeautifulSoup(html,"lxml") 9 try: 10 print(bsObj.h1.get_text()) 11 print(bsObj.find(id="mw-content-text").findAll("p")[0]) 12 print(bsObj.find(id="ca-edit").find("span").find("a").attrs[‘href‘]) 13 except AttributeError: 14 print("頁面缺少一些屬性!不過不用擔心!") 15 for link in bsObj.findAll("a", href=re.compile("^(/wiki/)")): 16 if ‘href‘ in link.attrs: 17 if link.attrs[‘href‘] not in pages: 18 # 我們遇到了新頁面 19 newPage = link.attrs[‘href‘] 20 print("----------------\n"+newPage) 21 pages.add(newPage) 22 getLinks(newPage) 23 getLinks("")
運行結果
遞歸爬取網頁原理:
三 采用Scrapy采集
高樓大廈都是從最簡單的一磚一瓦疊起來,寫網絡爬蟲也是很多簡單的重復的操作組成,找到頁面的關鍵信息和外鏈,然後再如此循環。而Scrapy庫,可以大幅度降低網頁鏈接查找(不用自己去搞一大堆的過濾條件和正則表達式)還可以降低識別的工作復雜度。
使用參考;https://scrapy-chs.readthedocs.io/zh_CN/latest/intro/tutorial.html
第一步 創建Scrapy項目
報錯,安裝scrapy,cmd-pip install scrapy
報錯,沒有安裝visual 14
重新安裝成功,再次執行
scrapy startproject tutorial
創建成功後,目錄結構如下
第二步 定義數據源,修改item(參考官網)
第三步 創建爬蟲class(參考官網)
第四步 進入spider目錄,然後運行爬蟲
報錯,缺少win32庫
pip install pywin32
再次運行成功
第一個Scrapy的helloworld基本完成,這個過程大致如下:
Scrapy為Spider的 start_urls
屬性中的每個URL創建了 scrapy.Request
對象,並將 parse
方法作為回調函數(callback)賦值給了Request。
Request對象經過調度,執行生成 scrapy.http.Response
對象並送回給spider parse()
方法。
如有用到,後面繼續深入學習Scrapy。
Python數據采集-開始爬蟲