You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Python中并行运行同一函数以实现多链接同时爬取

解决Python爬虫串行爬取速度慢的问题:多进程并行方案

嘿,我来帮你搞定这个多进程爬取的问题!面对5000个链接的串行爬取,确实会因为大部分时间都在等待网络响应而浪费效率,用多进程并行处理能帮你把速度提上来。

核心思路

串行爬取时,单个进程每次只处理一个链接,大部分时间处于等待状态。多进程可以同时发起多个请求,把等待的时间利用起来,大幅提升整体爬取效率。

具体实现方案

我们可以用Python标准库中的concurrent.futures.ProcessPoolExecutor来实现多进程并行,它的API非常简洁,容易上手。

步骤1:改造爬取函数

首先把原来遍历整个链接列表的函数,改成单个链接处理函数——每个进程负责处理一个链接:

import requests

def fetch_link(link):
    try:
        # 发起请求
        response = requests.get(link, timeout=5)
        # --- 这里写你的爬取逻辑(解析数据、保存结果等)---
        # 示例:打印成功信息
        print(f"✅ 成功获取链接: {link}")
        # 如果需要返回结果,可以在这里return处理后的数据
        return {"link": link, "status": response.status_code}
    except requests.exceptions.RequestException as e:
        # 处理请求异常(超时、连接失败等)
        print(f"❌ 获取链接失败 {link}: {str(e)}")
        return {"link": link, "status": "failed", "error": str(e)}

步骤2:用进程池批量处理链接

接下来创建进程池,把链接列表交给进程池并行处理:

from concurrent.futures import ProcessPoolExecutor

if __name__ == "__main__":
    # 你的5000个链接列表
    links = ["http://example.com", "http://test.com", ...]
    
    # 设置进程池大小:建议根据CPU核心数调整(比如核心数的2-4倍),同时别超过目标网站的承受能力
    max_workers = 8
    
    # 创建进程池并执行任务
    with ProcessPoolExecutor(max_workers=max_workers) as executor:
        # 用map方法把每个链接分配给进程池中的进程处理
        results = list(executor.map(fetch_link, links))
    
    # 可以在这里统一处理所有结果(比如保存到文件/数据库)
    print(f"\n📊 爬取完成,共处理 {len(results)} 个链接")

关键注意事项

  • if __name__ == "__main__": 必须加:这是Windows系统下多进程运行的必要条件,避免进程重复启动的问题。
  • 合理设置max_workers:不要盲目设太大,否则可能导致目标网站触发反爬机制(封禁IP),也会消耗本地过多资源。建议从8-16开始测试,根据实际情况调整。
  • 反爬应对:并行爬取容易被网站识别为爬虫,建议添加请求头(比如User-Agent模拟浏览器)、随机延迟(可以在fetch_link里加time.sleep(random.uniform(0.5, 2))),必要时使用代理池。
  • IO密集型任务可选线程池:如果你的爬取逻辑主要是等待网络响应(IO密集型),用ThreadPoolExecutor(把ProcessPoolExecutor替换成它)的开销更小,效率也差不多,因为线程切换成本比进程低。

备选方案:用multiprocessing.Pool

如果你习惯用更底层的multiprocessing模块,也可以这样写:

from multiprocessing import Pool
import requests

def fetch_link(link):
    # 和上面的fetch_link函数逻辑一致
    pass

if __name__ == "__main__":
    links = [...]
    with Pool(processes=8) as pool:
        results = pool.map(fetch_link, links)

这样应该能大幅提升你的爬取速度啦!记得根据目标网站的情况调整并发数,别太猛导致被封禁哦~

内容的提问来源于stack exchange,提问作者Soham Chakraborty

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.28 21:34:07