单/多线程--协程--异步爬虫

免责声明:本文仅做技术交流与学习... 

目录

了解进程和线程

单个线程(主线程)在执行

多线程

线程池

协程(爬虫多用)

假异步:(同步)

真异步:

爬虫代码模版

异步-爬虫

同步效果--19+秒

异步效果--7+秒


了解进程和线程

​
# -------------------->
# ------>
#       ------->
#               -------->
​
# 1-线程
#线程:执行一个软件后的操作---点赞,签到,评论等等
#进程:执行一个软件
​
​
一家公司里面人去做事.
1人,2人,多人...
(要合理分配,合理运用.)
--30万的资本,养不起10000人呀.
​
1个进程必须要有一个线程,--- 线程不是越多越好.
单线程/多线程
​
​
进程:资源单元
线程:执行单元
​
​
​
​
# 每一个py程序默认都有一个线程的,
print("111")
​

单个线程(主线程)在执行


多线程

from threading import Thread
# alt + enter 快捷键导包
​
def func(name):for i in range(1, 1000):print("func函数在执行---" + str(i),name)
​
​
# func()  # 这样写就是主线程执行.
​
# 创建线程对象,分配线程的任务是func   (公司招人要分配任务)
t = Thread(target=func,args=('my name xiaodi',))   # args的参数必须是一个元组.
# 启动线程:                       (员工先忙完手头工作,然后真正工作)
t.start()   # 线程的状态,可以开始工作的状态了,具体的执行时间由CPU决定.
​
t1 = Thread(target=func,args=('xiaosedi',))
t1.start()
​
# 主线程不会受到子线程(其他线程)的干扰.  主线程该干什么就干什么.
for i in range(1, 1000):print("主---" + str(i))
# 多个线程都输出到控制台上,就会乱.
​
# 传参在创建线程对象时也要传.
​
# 线程数由电脑的CPU决定,如果处理不好,反而会效率下降.
​


线程池

# 线程池 :一次性开辟一些线程,直接给线程池提交任务,具体的任务到底哪个线程执行,是由线程池分配的
from concurrent.futures.thread import ThreadPoolExecutor
​
​
def func(name):for i in range(1000):print(name, 'func函数执行', i)
​
​
# 创建一个有50个线程的线程池.(合理的利用资源~)
# -----执行10次func函数,每个func函数执行1000次.
with ThreadPoolExecutor(50) as t:#     t = ThreadPoolExecutor(50)for i in range(10):# 给线程去提交任务t.submit(func, name=f'线程{i}')
​
# 等待线程池中的任务全部执行完毕,才会继续执行
print('print执行了')


协程(爬虫多用)

import asyncio
import time
​
def func():print("函数开始")time.sleep(3)   # 当到此时,当前线程为阻塞状态,CPU不会为当前程序提供工作.print("函数结束")
func()
​
# 阻塞代码:(必须要等待某个结果等等
# input(等待输入)   time.sleep(强制等待)    requests(请求网络,client<->server有时间差,
# 程序基于 i(input) o(output) 操作时,线程机会处于阻塞状态,CPU就不会提供工作.
# ---阻塞的时候就会干等着,---怎么让CPU在干等着的时候也做点事情呢?--->协程!!!
​
# 协程:当程序遇见了io操作的时候,可以选择性的切换到其它任务上。
# 多任务异步操作:

假异步:(同步)

import asyncio
import time
​
​
async def func1():print('func1函数开始')time.sleep(3)  # 属于同步操作代码。# 只要在异步程序中出现了同步操作,异步就被中断# await asyncio.sleep(3)print('func1函数结束')
​
​
async def func2():print('func2函数开始')time.sleep(2)# await asyncio.sleep(2)print('func2函数结束')
​
​
async def func3():print('func3函数开始')time.sleep(4)# await asyncio.sleep(4)print('func3函数结束')
​
​
# 拿到函数的对象
f1 = func1()
f2 = func2()
f3 = func3()
tasks = [# 创建一个任务f1, f2, f3
]
start = time.time()
# 如果是多个任务,需要一个asyncio.wait(任务列表)搭配
asyncio.run(asyncio.wait(tasks))
print(time.time() - start)
​

9+秒结束!!! ---没有异步呀---

因为time是一个同步模块,

time.sleep()  # 属于同步操作代码。
# 只要在异步程序中出现了同步操作,异步就被中断

真异步:

import asyncio
import time
​
​
async def func1():print('func1函数开始')# time.sleep(3)         # 属于同步操作代码await asyncio.sleep(3)  # 异步休眠代码       --不是强制性的休眠,而是挂起,让他先去忙别的东西,等好了再回来.print('func1函数结束')
​
​
async def func2():print('func2函数开始')# time.sleep(2)await asyncio.sleep(2)print('func2函数结束')
​
​
async def func3():print('func3函数开始')# time.sleep(4)await asyncio.sleep(4)print('func3函数结束')#async def main():
#     f1 = func1()
#     f2 = func2()
#     f3 = func3()
#     tasks = [
#         f1,f2,f3
#         # 创建一个任务
#         # asyncio.create_task(func1()),
#         # asyncio.create_task(func2()),
#         # asyncio.create_task(func3())
#     ]
#     await asyncio.wait(tasks)
# start = time.time()
# asyncio.run(main())
# print(time.time() - start)
​
f1 = func1()
f2 = func2()
f3 = func3()
tasks = [f1, f2, f3# 创建一个任务
]
​
start = time.time()
# 如果是多个任务,需要一个asyncio.wait(任务列表)搭配
asyncio.run(asyncio.wait(tasks))
print(time.time() - start)

4+秒 , 好快呀...


爬虫代码模版

import asyncio
​
​
async def download(url):print('准备开始下载')# await asyncio.sleep(2) # 网络请求# requests.get(url)      # 异步效果中断,那怎么结合呢???print('下载完成')
​
​
async def main():urls = ['地址1','地址2','地址3',]# tasks = []# for url in urls:#    tasks.append(download(url))
​# 列表推导式写法 循环url列表,每循环一次,创建一个任务tasks = [download(url) for url in urls]await asyncio.wait(tasks)
​
​
asyncio.run(main())
​

requests.get(url) # 异步效果中断,那怎么结合呢???

只要出现同步操作,异步就会被终断.

-------->


异步-爬虫

因为requests模块是同步的,如果在异步协程中编写同步代码,异步效果没有。
​
如何解决?
更换支持异步的请求模块
aiohttp  == requests
pip install aiohttp
pip install aiofiles

同步效果--19+秒

import time
import requests
​
urls = ['https://www.cgwallpapers.com/wallpapers_free_wreoiux/wallpaper_christian_dimitrov_02_1920x1080.jpg','https://www.cgwallpapers.com/wallpapers_free_wreoiux/wallpaper_pablo_carpio_17_1920x1080.jpg','https://www.cgwallpapers.com/wallpapers_free_wreoiux/wallpaper_dejian_wu_04_1920x1080.jpg'
]
t = time.time()
for url in urls:res = requests.get(url).content# 文件名name = url.split('/')[-1]with open(name, 'wb') as f:f.write(res)
print(f'requests花费时间===》{time.time() - t}')
# requests花费时间===》19.635247230529785

异步效果--7+秒

import asyncio
import time
import aiofiles
import aiohttp
urls = ['https://www.cgwallpapers.com/wallpapers_free_wreoiux/wallpaper_christian_dimitrov_02_1920x1080.jpg','https://www.cgwallpapers.com/wallpapers_free_wreoiux/wallpaper_pablo_carpio_17_1920x1080.jpg','https://www.cgwallpapers.com/wallpapers_free_wreoiux/wallpaper_dejian_wu_04_1920x1080.jpg'
]
async def download(url):print('准备开始下载--->')# s = aiohttp.ClientSession()  == requests              #拿到对象# s.get() s.post  ===  requests.get() requests.post()# --------------------------------------# aiohttp                    requests# res.text()                  res.text# res.read()                  res.content# res.json()                  res.json()# --------------------------------------async with aiohttp.ClientSession() as s:async with s.get(url) as res:# 写入文件name = url.split('/')[-1]# 文件正常操作:# with open(name,'wb')as f:#     f.write(await res.read())# 文件异步操作:async with aiofiles.open(name, 'wb') as f:await f.write(await res.read())print('下载完成')
async def main(urls):tasks = [download(url) for url in urls]await asyncio.wait(tasks)
t = time.time()
asyncio.run(main(urls))
print(f'aiohttp花费时间===》{time.time() - t}')
# aiohttp花费时间===》7.244250774383545
​

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/41890.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

MinIO:开源对象存储解决方案的领先者

MinIO:开源对象存储解决方案的领先者 MinIO 是一款开源的对象存储系统&#xff0c;致力于提供高性能、可伸缩、安全的数据存储解决方案。 官方解释&#xff1a;MinIO 是一个基于Apache License v2。0开源协议的对象存储服务。它兼容亚马逊S3云存储服务接口&#xff0c;非常适…

WAIC:生成式 AI 时代的到来,高通创新未来!

目录 01 在终端侧算力上&#xff0c;动作最快的就是高通 02 模型优化&#xff0c;完成最后一块拼图 在WAIC上&#xff0c;高通展示的生成式AI创新让我们看到了未来的曙光。 生成式 AI 的爆发带来了意想不到的产业格局变化&#xff0c;其速度之快令人惊叹。 仅在一个月前&…

Vue + SpringBoot:el-upload组件单文件、多文件上传实战解析

文章目录 单文件上传后端前端 多文件上传后端前端 单文件上传 后端 PostMapping("/uploadDxfFile") public R uploadDxfFile(RequestParam(value "file", required true) MultipartFile multipartFile) throws Exception {// 文件校验工作if (multipar…

web Worker学习笔记 | 浏览器切换标签,定时器失效的解决办法

文章目录 web Workerweb Worker介绍 - 多线程解决方案浏览器多进程架构 web workers 的使用关闭worker引用其他js文件 浏览器切换标签&#xff0c;定时器失效的解决办法窗口可见性 API解决定时器失效的方案 web Worker web Worker介绍 - 多线程解决方案 Web Workers 是Html5提…

服务器数据恢复—DS5300存储raid5阵列数据恢复案例

服务器存储数据恢复环境&#xff1a; 某单位一台某品牌DS5300存储&#xff0c;1个机头4个扩展柜&#xff0c;50块硬盘组建2组RAID5磁盘阵列&#xff08;一组raid5阵列有27块成员盘&#xff0c;存放Oracle数据库文件&#xff1b;另外一组raid5阵列有23块成员盘&#xff09;。存储…

HashMap中的put()方法

一. HashMap底层结构 HashMap底层是由哈希表(数组),链表,红黑树构成,哈希表存储的类型是一个节点类型,哈希表默认长度为16,它不会每个位置都用,当哈希表中的元素个数大于等于负载因子(0.75)*哈希表长度就会扩容到原来的2倍 二. 底层的一些常量 三. HashMap的put()方法 当插入一…

ONLYOFFICE最新8.1版本——桌面编辑器简单测评

前言 大家好&#xff0c;我是小雨&#xff0c;看到最近ONLYOFFICE更新了最新的版本&#xff0c;更新了一下当前版本来具体的测评一下&#xff0c;先来看看官网提供的各类更新信息&#xff0c;下面是我找到的三个主页&#xff0c;包括功能演示链接&#xff0c;官网连接以及专门…

阿里云存储

传统存储面临的挑战 现如今&#xff0c;数据与土地、劳动力、资本、技术并称为五大生产要素&#xff0c;数据成为数字经济发展的重要引擎。大数据时代&#xff0c;数据处理的需求急剧增长&#xff0c;越来越多的智能设备以及新应用如区块链、机器学习训练和AI等产生大量的数据…

复分析——第10章——Θ函数应用(E.M. Stein R. Shakarchi)

第10章 Θ函数的应用 (Applications of Theta Functions) The problem of the representation of an integer n as the sum of a given number k of integral squares is one of the most celebrated in the theory of numbers. Its history may be traced back to Diopha…

CV03_mAP计算以及COCO评价标准

COCO数据集回顾&#xff1a;CV02_超强数据集&#xff1a;MSCOCO数据集的简单介绍-CSDN博客 1.1 简介 在目标检测领域中&#xff0c;mAP&#xff08;mean Average Precision&#xff0c;平均精度均值&#xff09;是一个广泛使用的性能评估指标&#xff0c;用于衡量目标检测模型…

短信验证码实现

一、设置AccessKey 创建用户并配置使用权限&#xff0c;使我们拥有调用 aliyunAPI 的权限&#xff0c;之后会生成 AccessKeyID 和 AccessKey密码&#xff0c;后面我们会使用到。需要注意的是 AccessKeyID 和 AccessKey密码生成后我们需要将他保存起来&#xff0c;否则后期无法查…

奇迹MU 骷髅战士在哪

BOSS分布图介绍 我为大家带来各地区怪物分布图。在游戏前期&#xff0c;很多玩家可能会不知道该去哪里寻找怪物&#xff0c;也不知道哪些怪物值得打。如果选择了太强的怪物&#xff0c;弱小的玩家可能会无法抵御攻击。如果选择了低等级的boss&#xff0c;收益可能并不理想。所…

智能家居安防系统教学解决方案

前言 随着科技的不断进步和智能家居概念的深入人心&#xff0c;智能家居安防系统作为智能家居领域的重要组成部分&#xff0c;其重要性日益凸显。智能家居安防系统不仅能够提供环境和人员的监测功能&#xff0c;还能够采取措施降低或避免人员伤亡及财产损失。因此&#xff0c;…

word文档没有保存就关闭了怎么恢复?找到正确的方法

昨天写教程的时候&#xff0c;终于完成了一个word文档&#xff0c;以为保存了就直接关了。word提醒我“是否保存”&#xff0c;我直接忽略了。动作一气呵成&#xff0c;毫不犹豫的关闭了。之后才发现我没有保存word文档。这种情况大家有遇到过吗?我们该如何在没有保存的情况下…

迎接AI新时代:GPT-5即将登场的巨大变革与应用前瞻

迎接AI新时代&#xff1a;GPT-5即将登场的巨大变革与应用前瞻 &#x1f48e;1. GPT-5 一年半后发布&#xff1a;AI新时代的来临1.1 GPT-5的飞跃&#xff1a;从高中生到博士生 &#x1f48e;2. GPT-5的潜在应用场景&#x1f48e;2.1 医疗诊断和健康管理&#x1f48e;2.2 教育领域…

ContextCapture - 开启三维世界的魔法之门

亲爱的朋友们&#xff0c;当我第一次接触到ContextCapture这款软件时&#xff0c;我的内心激动得难以平静。仿佛一位魔法师突然出现在我面前&#xff0c;向我展示了一个全新的世界。是的&#xff0c;这就是ContextCapture带给我的感觉 - 它不仅仅是一款软件&#xff0c;更是一把…

基于海思Hi3403V100方案开发双目1600万拼接相机测试截图

海思Hi3403V100平台SOC内置四核A55&#xff0c;提供高效且丰富和灵活的CPU资源&#xff0c;以满足客户计算和控制需求&#xff0c;并且集成单核MCU&#xff0c;已满足一些低延时要求较高场景。 多目相机PE108CB板是针对该芯片设计的一款多目凭借相机PCBA&#xff0c;硬件接口支…

7寸微型FPV无人机技术详解

对于7寸微型FPV&#xff08;First Person View&#xff0c;第一人称视角&#xff09;无人机技术的详解&#xff0c;可以从以下几个方面进行介绍&#xff1a; 一、定义与基本概念 FPV无人机&#xff0c;全称为“第一人称视角无人机”&#xff0c;它利用安装在无人机上的摄像头…

键盘异常的检测与解决方案

今天对象用Word写文档&#xff0c;按下Ctrl的时候&#xff0c;页面不停地上下滑动&#xff0c;导致无法正常编辑文本。 重启之后&#xff0c;仍然无法解决&#xff0c;推断是键盘坏了。 但是当按下Fn或其他功能键&#xff0c;焦点移除&#xff0c;页面就不会再抖动了。 现在…

3C电子制造行业MES系统,提高企业生产效率

随着科技的不断进步&#xff0c;3C电子制造行业正迎来传统工厂向数字化工厂转型的阶段。在这场变革中&#xff0c;MES系统发挥着重要的作用&#xff0c;成为了企业变革的“智慧大脑”&#xff0c;引领着生产流程的优化和升级。 那么&#xff0c;MES系统究竟有哪些功能&#xf…