Python爬取知乎評論:多線程與異步爬蟲的性能優化

1. 知乎評論爬取的技術挑戰

知乎的評論數據通常采用動態加載(Ajax),這意味著直接使用**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">requests</font>**+**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">BeautifulSoup</font>**無法獲取完整數據。此外,知乎還設置了反爬機制,包括:

  • 請求頭(Headers)驗證(如**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">User-Agent</font>****<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">Referer</font>**
  • Cookie/Session 校驗(未登錄用戶只能獲取部分數據)
  • 頻率限制(頻繁請求可能導致IP被封)

因此,我們需要:

  1. 模擬瀏覽器請求(攜帶Headers和Cookies)
  2. 解析動態API接口(而非靜態HTML)
  3. 優化爬取速度(多線程/異步)

2. 獲取知乎評論API分析

(1)查找評論API

打開知乎任意一個問題(如 **<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">https://www.zhihu.com/question/xxxxxx</font>**),按**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">F12</font>**進入開發者工具,切換到**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">Network</font>**選項卡,篩選**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">XHR</font>**請求

(2)解析評論數據結構

評論通常嵌套在**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">data</font>**字段中,結構如下:

{"data": [{"content": "評論內容","author": { "name": "用戶名" },"created_time": 1620000000}],"paging": { "is_end": false, "next": "下一頁URL" }
}

我們需要遞歸翻頁(**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">paging.next</font>**)爬取所有評論。

3. Python爬取知乎評論的三種方式

(1)單線程爬蟲(基準測試)

使用**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">requests</font>**庫直接請求API,逐頁爬取:

import requests
import timedef fetch_comments(question_id, max_pages=5):base_url = f"https://www.zhihu.com/api/v4/questions/{question_id}/answers"headers = {"User-Agent": "Mozilla/5.0","Cookie": "你的Cookie"  # 登錄后獲取}comments = []for page in range(max_pages):url = f"{base_url}?offset={page * 10}&limit=10"resp = requests.get(url, headers=headers).json()for answer in resp["data"]:comments.append(answer["content"])time.sleep(1)  # 避免請求過快return commentsstart_time = time.time()
comments = fetch_comments("12345678")  # 替換為知乎問題ID
print(f"單線程爬取完成,耗時:{time.time() - start_time:.2f}秒")

缺點:逐頁請求,速度慢(假設每頁1秒,10頁需10秒)。

(2)多線程爬蟲(ThreadPoolExecutor)

使用**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">concurrent.futures</font>**實現多線程并發請求:

from concurrent.futures import ThreadPoolExecutordef fetch_page(page, question_id):url = f"https://www.zhihu.com/api/v4/questions/{question_id}/answers?offset={page * 10}&limit=10"headers = {"User-Agent": "Mozilla/5.0"}resp = requests.get(url, headers=headers).json()return [answer["content"] for answer in resp["data"]]def fetch_comments_multi(question_id, max_pages=5, threads=4):with ThreadPoolExecutor(max_workers=threads) as executor:futures = [executor.submit(fetch_page, page, question_id) for page in range(max_pages)]comments = []for future in futures:comments.extend(future.result())return commentsstart_time = time.time()
comments = fetch_comments_multi("12345678", threads=4)
print(f"多線程爬取完成,耗時:{time.time() - start_time:.2f}秒")

優化點

  • 線程池控制并發數(避免被封)
  • 比單線程快約3-4倍(4線程爬10頁僅需2-3秒)

(3)異步爬蟲(Asyncio + aiohttp)

使用**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">aiohttp</font>**實現異步HTTP請求,進一步提高效率:

import aiohttp
import asyncio
import time# 代理配置
proxyHost = "www.16yun.cn"
proxyPort = "5445"
proxyUser = "16QMSOML"
proxyPass = "280651"async def fetch_page_async(session, page, question_id):url = f"https://www.zhihu.com/api/v4/questions/{question_id}/answers?offset={page * 10}&limit=10"headers = {"User-Agent": "Mozilla/5.0"}async with session.get(url, headers=headers) as resp:data = await resp.json()return [answer["content"] for answer in data["data"]]async def fetch_comments_async(question_id, max_pages=5):# 設置代理連接器proxy_auth = aiohttp.BasicAuth(proxyUser, proxyPass)connector = aiohttp.TCPConnector(limit=20,  # 并發連接數限制force_close=True,enable_cleanup_closed=True,proxy=f"http://{proxyHost}:{proxyPort}",proxy_auth=proxy_auth)async with aiohttp.ClientSession(connector=connector) as session:tasks = [fetch_page_async(session, page, question_id) for page in range(max_pages)]comments = await asyncio.gather(*tasks)return [item for sublist in comments for item in sublist]if __name__ == "__main__":start_time = time.time()comments = asyncio.run(fetch_comments_async("12345678"))  # 替換為知乎問題IDprint(f"異步爬取完成,耗時:{time.time() - start_time:.2f}秒")print(f"共獲取 {len(comments)} 條評論")

優勢

  • 無GIL限制,比多線程更高效
  • 適合高并發IO密集型任務(如爬蟲)

4. 性能對比與優化建議

爬取方式10頁耗時(秒)適用場景
單線程~10少量數據,簡單爬取
多線程(4線程)~2.5中等規模,需控制并發
異步(Asyncio)~1.8大規模爬取,高并發需求

優化建議

  1. 控制并發數:避免觸發反爬(建議10-20并發)。
  2. 隨機延遲**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">time.sleep(random.uniform(0.5, 2))</font>** 模擬人類操作。
  3. 代理IP池:防止IP被封(如使用**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">requests</font>**+**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">ProxyPool</font>**)。
  4. 數據存儲優化:異步寫入數據庫(如**<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">MongoDB</font>****<font style="color:rgb(64, 64, 64);background-color:rgb(236, 236, 236);">MySQL</font>**)。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/pingmian/87932.shtml
繁體地址,請注明出處:http://hk.pswp.cn/pingmian/87932.shtml
英文地址,請注明出處:http://en.pswp.cn/pingmian/87932.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

軟件系統測試的基本流程

軟件系統測試流程是確保軟件質量的規范化過程&#xff0c;涵蓋從測試準備到最終上線評估的全周期&#xff0c;通常分為以下6個核心階段&#xff0c;各階段緊密銜接、形成閉環&#xff1a; 一、測試啟動與規劃階段 核心目標&#xff1a;明確“測什么、誰來測、怎么測”&#xff…

使用Linux操作MySQL數據庫分批導出數據為.SQL文件

當數據庫某張數據量非常大的表進行其他操作&#xff0c;需要先進行導出時&#xff1b; 先用linux進入操作環境&#xff0c; 1.添加一個export_mysql_batches.sh腳本文件&#xff0c; #!/bin/bash# 數據庫連接配置 DB_HOST"36.33.0.138:3306" DB_USER"devuser&qu…

LeetCode 算法題解:鏈表與二叉樹相關問題 打打卡

LeetCode 算法題解&#xff1a;鏈表與二叉樹相關問題 在算法學習和實踐中&#xff0c;LeetCode 是一個非常好的平臺&#xff0c;它包含了各種各樣的算法題目&#xff0c;有助于我們提升編程能力和解決問題的能力。本文將詳細講解在 leetcoding.cpp 文件中實現的一些鏈表和二叉樹…

故宮票價監控接口分析(一)

故宮票價監控接口分析(一) 對爬蟲、逆向感興趣的同學可以查看文章,一對一小班教學(系統理論和實戰教程)、提供接單兼職渠道:https://blog.csdn.net/weixin_35770067/article/details/142514698 本文內容僅供學習和參考之用,不得用于商業目的。作者對文中內容的準確性、完整…

AWS OpenSearch Dev Tools使用

# 創建通用索引模版 PUT _template/aws-waf_logs_template {"index_patterns": ["aws-waf-logs-*"],"mappings": {"properties": {"timestamp": {"type": "date"}}} }# 設置單個索引格式 PUT /aws-waf-…

git-安裝 Gerrit Hook 自動生成changeid

要在 Git 中安裝 Gerrit Hook 以自動生成 Change-ID&#xff0c;可以按照以下步驟操作&#xff1a; 全局鉤子配置&#xff08;推薦&#xff09; 創建全局鉤子目錄并下載 Gerrit 提供的 commit-msg 鉤子腳本&#xff0c;確保所有倉庫共享該配置&#xff1a; mkdir -p ~/.githook…

Excel 的多線程特性

Excel 本身并不是完全多線程的應用程序&#xff0c;但它在某些操作和功能上支持多線程處理。以下是對 Excel 是否多線程的詳細解答&#xff0c;結合你之前提到的 VBA/COM 自動化代碼和受保護視圖問題&#xff0c;提供清晰且準確的分析。 Excel 的多線程特性計算引擎的多線程支持…

【嵌入式ARM匯編】-操作系統基礎(一)

操作系統基礎(一) 文章目錄 操作系統基礎(一)1、操作系統架構概述2、用戶模式與內核模式3、進程4、系統調用5、對象和句柄我們想要逆向的程序幾乎從來不會在真空中執行。相反,程序通常在正在運行的操作系統(例如 Linux、Windows 或 macOS)的上下文中運行。因此,了解這些…

[創業之路-474]:企業經營層 - 小米與華為多維對比分析(2025年視角),以后不要把這兩家公司放在同一個維度上 進行比較了

一、行業定位與市場角色不同華為&#xff1a;用技術手段解決行業的難題&#xff0c;順便賺錢技術驅動型硬科技企業&#xff1a;以通信設備起家&#xff0c;延伸至智能手機、芯片、操作系統&#xff08;鴻蒙&#xff09;、云計算、智能汽車等領域&#xff0c;構建“云-管-端”全…

C#基礎篇(06)抽象類與接口詳解區別

抽象類是 C# 面向對象編程中的一個重要概念&#xff0c;它介于普通類和接口之間&#xff0c;提供了一種定義部分實現并要求派生類完成其余部分的機制。一、C# 中的抽象類抽象類是 C# 面向對象編程中的一個重要概念&#xff0c;它介于普通類和接口之間&#xff0c;提供了一種定義…

使用Python將PDF轉換成word、PPT

在現代企業環境中,文檔格式的轉換是一項普遍且關鍵的需求。PDF(Portable Document Format)作為一種最終的、通常不可編輯的“打印”狀態格式,被廣泛用于分發和歸檔。然而,內容的創建、協作和修改主要在Microsoft Office套件中進行,特別是Word(DOCX)和PowerPoint(PPTX)…

香港風水(原生)林地的邏輯分類器

風水林是香港的原生林地&#xff0c;由于地處偏遠、地形崎嶇以及當地居民的信仰&#xff0c;這些林地得以保存完好。在香港&#xff0c;我們可以追溯到1924年的航拍圖像記錄&#xff0c;這些黑白航拍圖像已經幫助我們劃分和區分了林地、草地和灌木叢。然后&#xff0c;通過二戰…

[Swarm] Result對象 | 智能體切換 | Response對象 | muduo review

第5章&#xff1a;結果對象 歡迎回到swarm&#xff01; 在上一章第4章&#xff1a;功能中&#xff0c;我們學習了如何通過定義Python功能賦予智能體技能。我們見證了當AI決策調用時&#xff0c;Swarm框架如何執行這些功能。 當前&#xff0c;我們的功能僅返回簡單字符串如&q…

[2-02-02].第04節:環境搭建 - Linux搭建ES集群環境

ElasticSearch學習大綱 一、ES集群規劃&#xff1a; 關系型數據庫&#xff08;比如Mysql&#xff09;非關系型數據庫&#xff08;Elasticsearch&#xff09;非關系型數據庫&#xff08;Elasticsearch&#xff09;centos7hadoop103192.168.148.3centos7hadoop104192.168.148.4c…

部署并運行Spike-Driven-Transformer或QKFormer

部署并運行Spike-Driven-Transformer或QKFormer 我將指導你如何部署和運行Spike-Driven-Transformer或QKFormer代碼,并在CIFAR-10、CIFAR-100和ImageNet-1K數據集上進行訓練和測試。 1. 環境準備 首先需要設置Python環境并安裝必要的依賴項: # 創建conda環境(推薦) con…

爬蟲-request處理POST

1.概念很少在URL寫參數&#xff0c;都在form data里面POST 的主要作用是將客戶端的數據提交給服務器。這些數據可以是表單輸入、文件內容、JSON 數據、XML 數據等等POST 請求攜帶的數據放在 HTTP 消息的請求體中。這與 GET 請求形成鮮明對比&#xff1a;GET 請求的數據通常附加…

免U盤一鍵重裝系統

免U盤一鍵重裝系統 簡單介紹 詳細的看GitHub項目首頁 GitHub地址 # 下載腳本 curl -O https://cnb.cool/bin456789/reinstall/-/git/raw/main/reinstall.sh || wget -O reinstall.sh $_ # 重裝系統 bash reinstall.sh ubuntu # 重啟 rebootPS: 重啟過程中, 可能需要手動選擇r…

自動化一次通過率

自動化測試中的“一次通過率”&#xff08;First-pass Pass Rate&#xff09;?? 是指自動化測試腳本在首次執行&#xff08;無人工干預、無重試&#xff09;?時&#xff0c;?成功通過的測試用例數占總執行用例數的百分比。?核心概念解析???“一次”的含義??首次運行?…

111111事件

1.抽取 minio 當做文件對象存儲服務器&#xff0c;在上面封裝一層api&#xff0c;方便操作。 &#xff08;文件上傳&#xff0c;指定路徑上傳&#xff0c;隨機命名上傳&#xff0c;前端獲取token直接傳&#xff0c;適合大對象&#xff0c;圖片壓縮&#xff09; 2.規范整個java項…

Qt的ui文件的編譯和使用

Qt中的ui文件編譯的類 要么繼承 &#xff0c;要么實例化一個變量個人覺得還是繼承好點&#xff0c;這樣每次調用控件時&#xff0c;不用都要在控件前加上 ui.1 上面使用的是繼承的關系&#xff0c;這樣就可以直接使用控件.屬性&#xff0c;而不用 ui.控件.樹形2 QT中UI文件…