Python網路爬蟲精要
程序員大咖
點擊右側關注,免費進階高級!
alphardex,Pythonista && Otaku,努力轉行中的一位測繪人員。
地址:zhihu.com/people/ban-zai-liu-shang
目的
學習如何從互聯網上獲取數據。數據科學必須掌握的技能之一。
本文所用到的第三方庫如下: requests, parsel, selenium
requests負責向網頁發送HTTP請求並得到響應,parsel負責解析響應字元串,selenium負責JavaScript的渲染。
網路爬蟲是什麼
網路爬蟲是一種按照一定的規則,自動地抓取網站信息的程序或者腳本。
如何爬取網站信息
寫爬蟲之前,我們必須確保能夠爬取目標網站的信息。
不過在此之前必須弄清以下三個問題:
網站是否已經提供了api
網站是靜態的還是動態的
網站是否有反爬的對策
情形1:開放api的網站
一個網站倘若開放了api,那你就可以直接GET到它的json數據。
比如xkcd的about頁就提供了api供你下載
import get "https://xkcd.com/614/info.0.json"
requests.
).json()
那麼如何判斷一個網站是否開放api呢?有3種方法:
在站內尋找api入口
用搜索引擎搜索「某網站 api」
抓包。有的網站雖然用到了ajax(比如果殼網的瀑布流文章),但是通過抓包還是能夠獲取XHR里的json數據的。
怎麼抓包:F12 - Network - F5刷新即可 | 或者用fiddle等工具也可以
情形2:不開放api的網站
如果此網站是靜態頁面,那麼你就可以用requests庫發送請求,再用HTML解析庫(lxml、parsel等)來解析響應的text
解析庫強烈推薦parsel,不僅語法和css選擇器類似,而且速度也挺快,Scrapy用的就是它。
你需要了解一下css選擇器的語法(xpath也行),並且學會看網頁的審查元素。
比如獲取konachan的所有原圖鏈接
from get "https://konachan.com/post") text text "a.directlink::attr(href)").extract()
res = requests.
tree = Selector(
imgs = tree.css(
如果此網站是動態頁面,先用selenium來渲染JS,再用HTML解析庫來解析driver的page_source。
比如獲取hitomi.la的數據(這裡把chrome設置成了無頭模式)
driver.get("https://hitomi.la/type/gamecg-all-1.html")from selenium import webdriver
options = webdriver.ChromeOptions()
options.add_argument("--headless")
driver = webdriver.Chrome(options=options)
tree = Selector(text=driver.page_source)
gallery_content = tree.css(".gallery-content > div")
情形3:反爬的網站
目前的反爬策略常見的有:驗證碼、登錄、封ip等。
驗證碼:利用打碼平台破解(如果硬上的話用opencv或keras訓練圖)
登錄:利用requests的post或者selenium模擬用戶進行模擬登陸
封ip:買些代理ip(免費ip一般都不管用),requests中傳入proxies參數即可
其他防反爬方法:偽裝User-Agent,禁用cookies等
推薦用fake-useragent來偽裝User-Agent
from fake_useragent import UserAgent
headers = {"User-Agent": UserAgent().random}
res = requests.get(url, headers=headers)
如何編寫結構化的爬蟲
如果能成功地爬取網站信息,那麼你已經成功了一大半。
其實爬蟲的架構很簡單,無非就是創造一個tasklist,對tasklist里的每一個task調用crawl函數。
大多數網頁的url構造都是有規律的,你只需根據它用列表推倒式來構造出tasklist對於那些url不變的動態網頁,先考慮抓包,不行再用selenium點擊下一頁
如果追求速度的話,可以考慮用concurrent.futures或者asyncio等庫。
import from import from import
domain =
"https://www.doutula.com"
def
crawl(url)
:res = requests.get(url)
tree = Selector(text=res.text)
imgs = tree.css(
"img.lazy::attr(data-original)"
).extract()# save the imgs ...
if
__name__ =="__main__"
:tasklist = [
f"
{domain}
/article/list/?page={i}
"for
iin
range(1
,551
)]with
futures.ThreadPoolExecutor(50
)as
executor:executor.map(crawl, tasklist)
數據存儲的話,看你的需求,一般都是存到資料庫中,只要熟悉對應的驅動即可。
常用的資料庫驅動有:pymysql(MySQL),pymongo(MongoDB)
如果你需要框架的話
文章讀到這裡,你應該對爬蟲的基本結構有了一個清晰的認識,這時你可以去上手框架了。
輕量級框架(looter):https://github.com/alphardex/looter
工業級框架(scrapy):https://github.com/scrapy/scrapy
【點擊成為源碼大神】


※使用Python自動生成報表以郵件發送
※婚禮小記:用Twilio,Python和Google打造我的自動化婚禮
TAG:Python開發 |