使用多线程或异步技术提高图片抓取效率

本文涉及的产品
实时计算 Flink 版,5000CU*H 3个月
检索分析服务 Elasticsearch 版,2核4GB开发者规格 1个月
大数据开发治理平台 DataWorks,不限时长
简介: 图片抓取是爬虫技术中常见的需求,但是图片抓取的效率受到很多因素的影响,比如网速、网站反爬机制、图片数量和大小等。本文将介绍如何使用多线程或异步技术来提高图片抓取的效率,以及如何使用爬虫代理IP来避免被网站拒绝服务

亿牛云代理.jpg

导语

图片抓取是爬虫技术中常见的需求,但是图片抓取的效率受到很多因素的影响,比如网速、网站反爬机制、图片数量和大小等。本文将介绍如何使用多线程或异步技术来提高图片抓取的效率,以及如何使用爬虫代理IP来避免被网站封禁。

概述

多线程和异步技术都是利用计算机的并发能力来提高程序的执行速度。多线程是指在一个进程中创建多个线程,每个线程可以独立地执行一部分任务,从而实现任务的并行处理。异步技术是指在一个线程中使用非阻塞的方式来执行任务,当遇到耗时的操作时,不会等待其完成,而是继续执行其他任务,从而实现任务的并发处理。使用多线程或异步技术可以有效地减少图片抓取的等待时间,提高图片抓取的效率。爬虫代理IP是指通过第三方服务器来访问目标网站,从而隐藏自己的真实IP地址。使用爬虫代理IP可以有效地防止被目标网站识别和封禁,提高图片抓取的成功率。

正文

本文将以Python语言为例,介绍如何使用多线程或异步技术来实现图片抓取,并使用亿牛云爬虫代理来提供代理IP服务。首先,需要导入一些必要的模块,如requests、threading、asyncio、aiohttp等:

# 导入模块
import requests
import threading
import asyncio
import aiohttp

然后,需要定义一个函数来获取图片的URL列表,这里假设目标网站是https://unsplash.com/,一个提供免费高清图片的网站。可以使用requests模块来发送HTTP请求,并使用BeautifulSoup模块来解析HTML文档,提取图片的URL:

# 定义函数获取图片URL列表
def get_image_urls():
    # 目标网站URL
    url = 'https://unsplash.com/'
    # 亿牛云 爬虫代理域名、端口、用户名、密码
    proxy_host = 'http://www.16yun.cn'
    proxy_port = '8080'
    proxy_user = '16YUN'
    proxy_pass = '16IP'
    # 构造代理URL
    proxy_url = f'{proxy_user}:{proxy_pass}@{proxy_host}:{proxy_port}'
    # 构造代理字典
    proxies = {
   
   
        'http': proxy_url,
        'https': proxy_url
    }
    # 发送HTTP请求,获取响应内容
    response = requests.get(url, proxies=proxies)
    html = response.text
    # 解析HTML文档,提取图片URL
    from bs4 import BeautifulSoup
    soup = BeautifulSoup(html, 'lxml')
    images = soup.find_all('img', class_='oCCRx')
    image_urls = [image['src'] for image in images]
    # 返回图片URL列表
    return image_urls

接下来,需要定义一个函数来下载并保存图片,这里假设将图片保存在当前目录下的images文件夹中。可以使用requests模块来下载图片,并使用os模块来创建文件夹和文件:

# 定义函数下载并保存图片
def download_and_save_image(image_url):
    # 亿牛云 爬虫代理域名、端口、用户名、密码
    proxy_host = 'http://www.16yun.cn'
    proxy_port = '8080'
    proxy_user = '16YUN'
    proxy_pass = '16IP'
    # 构造代理URL
    proxy_url = f'{proxy_user}:{proxy_pass}@{proxy_host}:{proxy_port}'
    # 构造代理字典
    proxies = {
   
   
        'http': proxy_url,
        'https': proxy_url
    }
    # 下载图片,获取图片内容
    response = requests.get(image_url, proxies=proxies)
    image_data = response.content
    # 创建images文件夹,如果不存在
    import os
    if not os.path.exists('images'):
        os.mkdir('images')
    # 从图片URL中提取图片文件名
    image_name = image_url.split('/')[-1]
    # 拼接图片文件路径
    image_path = os.path.join('images', image_name)
    # 保存图片文件
    with open(image_path, 'wb') as f:
        f.write(image_data)

最后,需要定义一个主函数来调用上述两个函数,并使用多线程或异步技术来提高图片抓取的效率。这里分别介绍两种方法:

  • 使用多线程技术:可以使用threading模块来创建多个线程对象,并将下载并保存图片的函数作为线程的目标函数,将图片URL作为线程的参数,然后启动所有线程,并等待所有线程结束:
# 定义主函数使用多线程技术
def main_threading():
    # 获取图片URL列表
    image_urls = get_image_urls()
    # 创建空列表存储线程对象
    threads = []
    # 遍历图片URL列表,创建并启动线程对象
    for image_url in image_urls:
        # 创建线程对象,指定目标函数和参数
        thread = threading.Thread(target=download_and_save_image, args=(image_url,))
        # 将线程对象添加到列表中
        threads.append(thread)
        # 启动线程对象
        thread.start()
    # 遍历线程对象列表,等待所有线程结束
    for thread in threads:
        thread.join()
  • 使用异步技术:可以使用asyncio模块来创建一个事件循环对象,并将下载并保存图片的函数改写为一个异步函数,使用aiohttp模块来发送异步HTTP请求,并使用asyncio模块的gather函数来收集所有的异步任务,并在事件循环中执行:
# 定义主函数使用异步技术
def main_asyncio():
    # 获取图片URL列表
    image_urls = get_image_urls()
    # 创建事件循环对象
    loop = asyncio.get_event_loop()
    # 定义异步函数下载并保存图片
    async def download_and_save_image_async(image_url):
        # 亿牛云 爬虫代理域名、端口、用户名、密码
        proxy_host = 'http://www.16yun.cn'
        proxy_port = '8080'
        proxy_user = '16YUN'
        proxy_pass = '16IP'
        # 构造代理URL
        proxy_url = f'{proxy_user}:{proxy_pass}@{proxy_host}:{proxy_port}'
        # 构造代理字典
        proxies = {
   
   
            'http': proxy_url,
            'https': proxy_url
        }
        # 使用aiohttp模块发送异步HTTP请求,获取图片内容
        async with aiohttp.ClientSession() as session:
            async with session.get(image_url, proxy=proxy_url) as response:
                image_data = await response.read()
        # 创建images文件夹,如果不存在
        import os
        if not os.path.exists('images'):
            os.mkdir('images')
        # 从图片URL中提取图片文件名
        image_name = image_url.split('/')[-1]
        # 拼接图片文件路径
        image_path = os.path.join('images', image_name)
        # 保存图片文件
        with open(image_path, 'wb') as f:
            f.write(image_data)
    # 创建空列表存储异步任务对象
    tasks = []
    # 遍历图片URL列表,创建并添加异步任务对象
    for image_url in image_urls:
        # 创建异步任务对象,指定异步函数和参数
        task = asyncio.ensure_future(download_and_save_image_async(image_url))
        # 将异步任务对象添加到列表中
        tasks.append(task)
    # 使用asyncio模块的gather函数收集所有的异步任务对象
    tasks = asyncio.gather(*tasks)
    # 在事件循环中执行所有的异步任务对象,并等待其完成
    loop.run_until_complete(tasks)

结语

本文介绍了如何使用多线程或异步技术来提高图片抓取的效率,以及如何使用代理IP来避免被网站封禁。通过使用多线程或异步技术,可以有效地减少图片抓取的等待时间,提高图片抓取的效率。通过使用代理IP,可以有效地防止被目标网站识别和封禁,提高图片抓取的成功率。本文以Python语言为例,给出了相应的代码实现,供读者参考。

相关文章
|
4月前
|
Python
【Python30天速成计划】10.异步以及多进程和多线程
【Python30天速成计划】10.异步以及多进程和多线程
|
2月前
|
安全 Python
Python中的并发编程:多线程与多进程技术探究
本文将深入探讨Python中的并发编程技术,重点介绍多线程和多进程两种并发处理方式的原理、应用场景及优缺点,并结合实例分析如何在Python中实现并发编程,以提高程序的性能和效率。
|
2月前
|
NoSQL 数据处理 调度
【Redis深度专题】「踩坑技术提升」探索Redis 6.0为何必须启用多线程以提升性能与效率
【Redis深度专题】「踩坑技术提升」探索Redis 6.0为何必须启用多线程以提升性能与效率
245 0
|
2月前
|
Python
Python学习之路 02 之分支结构
Python学习之路 02 之分支结构
451 0
Python学习之路 02 之分支结构
|
2月前
|
Java Python 开发者
Python 学习之路 01基础入门---【Python安装,Python程序基本组成】
线程池详解与异步任务编排使用案例-xian-cheng-chi-xiang-jie-yu-yi-bu-ren-wu-bian-pai-shi-yong-an-li
455 2
Python 学习之路 01基础入门---【Python安装,Python程序基本组成】
|
1天前
|
存储 缓存 前端开发
Java串口通信技术探究3:RXTX库线程 优化系统性能的SerialPortEventListener类
Java串口通信技术探究3:RXTX库线程 优化系统性能的SerialPortEventListener类
9 3
|
2天前
|
Dart 前端开发 安全
【Flutter前端技术开发专栏】Flutter中的线程与并发编程实践
【4月更文挑战第30天】本文探讨了Flutter中线程管理和并发编程的关键性,强调其对应用性能和用户体验的影响。Dart语言提供了`async`、`await`、`Stream`和`Future`等原生异步支持。Flutter采用事件驱动的单线程模型,通过`Isolate`实现线程隔离。实践中,可利用`async/await`、`StreamBuilder`和`Isolate`处理异步任务,同时注意线程安全和性能调优。参考文献包括Dart异步编程、Flutter线程模型和DevTools文档。
【Flutter前端技术开发专栏】Flutter中的线程与并发编程实践
|
8天前
|
缓存 Java 编译器
第一章 Java线程池技术应用
第一章 Java线程池技术应用
13 0
|
9天前
|
并行计算 算法 安全
Java从入门到精通:2.1.3深入学习Java核心技术——掌握Java多线程编程
Java从入门到精通:2.1.3深入学习Java核心技术——掌握Java多线程编程
|
9天前
|
并行计算 算法 Java
Java中的多线程技术实现与应用
【4月更文挑战第23天】本文将深入探讨Java中的多线程技术,包括其基本概念、实现方法以及在实际应用中的优势。我们将通过实例代码和应用场景,详细解析多线程技术在Java中的应用,以期帮助读者更好地理解和掌握这一技术。

相关实验场景

更多