python的多线程和多进程
首先需要明确的是,多进程和其他语言的一样,能够利用多核cpu,但是python由于GIL的存在,多线程在执行的时候,实际上,每一时刻只有一个线程在执行。相当于是单线程。然而多线程在某些情况下,还是能够起到加速的效果。
需要了解的是,程序的耗时一般消耗在IO和CPU上,按照占比不同,一般分为IO密集型或者CPU密集型。比如文件读写、网络传输,磁盘IO等,属于IO密集型,而矩阵计算、数值计算这种就属于CPU密集型。在单线程中,遇见IO操作的时候,CPU会阻塞,直到IO操作完成,花费的时间成本为IO耗时加CPU耗时。但是在多线程中,遇见IO操作的时候,该线程会交出GIL,其他线程可以继续运行,这样可以让CPU和IO并行。因此,如果是IO密集型,即在代码中,主要是进行IO读取,那么多线程仍然能够起到加速左右,值得注意的是,这里的加速效果应该是来自于处理IO的设备,支持并行IO,即同一时刻,能够处理多个IO请求。反之,如果是CPU密集型,IO耗时忽略不计的话,此时多线程相当于是单线程,同时考虑到线程的上下文切换,那么多线程的运行时间反而会更多。
线程池的使用方法submit和map
python中concurrent.futures这个类提供了线程池和进程池的接口。as_completed按照任务的完成时间返回,map按照任务的添加时间返回
我们可以通过submit或map添加任务,但使用起来存在细微差别。
一般通过submit得到一个包含future对象的列表,然后通过concurrent.futures.as_completed去遍历这个列表,该方法会阻塞,可以设置超时时间。每当有任务完成的时候,就能通过future.result()得到任务执行的结果,该方法同样会阻塞,可以设置超时时间。因此通过这种方法,输出是按照任务执行完成的时间排序的。
当然,我们也可以不用as_completed去遍历,这样就按照任务的顺序返回。因为每个任务如果没完成就阻塞,完成了就添加。
import concurrent.futures
import timedef task(times):# 模拟任务执行time.sleep(times)return timesdef main():num_threads = 3with concurrent.futures.ThreadPoolExecutor(max_workers=num_threads) as executor:# 提交任务到线程池# submitfutures = [executor.submit(task, t) for t in [7, 1, 3, 8]]# # 收集每个任务的结果results = []# for future in concurrent.futures.as_completed(futures):# result = future.result()# results.append(result)for future in futures:result = future.result()results.append(result)# map# results = []# futures = executor.map(task, [7, 1, 3, 8])# for future in futures:# results.append(future)print(f"results = {results}")if __name__ == "__main__":main()
上面两种submit,依次输出1 3 7 8和7 1 3 8
map函数则不太一样,第一个参数是需要线程执行的函数,第二个参数是一个迭代器,会依此将参数应用到线程函数中。返回结果和列表的顺序一样。返回7 1 3 8
多线程和多进程的对比
线程安全
import concurrent.futures
import random
from threading import Lock
import time# 共享变量
shared_variable = 0
# 锁对象,用于保护共享变量的访问
lock = Lock()def task(task_id):global shared_variable# 模拟任务执行# 获取锁,确保对共享变量的访问是线程安全的for _ in range(1000000):with lock:shared_variable += 1# shared_variable += 1def main():num_threads = 2with concurrent.futures.ThreadPoolExecutor(max_workers=num_threads) as executor:# 提交任务到线程池futures = [executor.submit(task, i) for i in range(2)]# 收集每个任务的结果results = []for future in concurrent.futures.as_completed(futures):result = future.result()results.append(result)print(f"results = {results}")print(f"shared_variable = {shared_variable}")if __name__ == "__main__":main()
注释掉上面代码的lock,试试加锁和不加锁,可以很清晰的看到,加锁的时候不会有竞争冒险,而不加锁则可能有竞争冒险。因为几率是比较小的,观察不到的话,可以加大循环的次数。
相关文章:

python的多线程和多进程
首先需要明确的是,多进程和其他语言的一样,能够利用多核cpu,但是python由于GIL的存在,多线程在执行的时候,实际上,每一时刻只有一个线程在执行。相当于是单线程。然而多线程在某些情况下,还是能…...

基于SpringBoot+Vue+uniapp的时间管理小程序的详细设计和实现(源码+lw+部署文档+讲解等)
详细视频演示 请联系我获取更详细的演示视频 项目运行截图 技术框架 后端采用SpringBoot框架 Spring Boot 是一个用于快速开发基于 Spring 框架的应用程序的开源框架。它采用约定大于配置的理念,提供了一套默认的配置,让开发者可以更专注于业务逻辑而不…...
HMAC-MD5参数签名算法
更多中电联在线工具 HMAC-MD5 是一种基于 MD5 哈希函数的消息认证码(MAC)算法。它用于确保消息的完整性和认证,通常用于数据传输和 API 请求。其基本步骤如下: 密钥准备:选择一个密钥(K)&#…...

【word】文章里的表格边框是双杠
日常小伙伴们遇到word里插入的表格,边框是双杠的,直接在边框和底纹里修改边框的样式就可以,但我今天遇到的这个有点特殊,先看看表格在word里的样式是怎么样,然后我们聊聊如何解决。 这个双杠不是边框和底纹的设置原因…...

我常用的两个单例模式写法 (继承Mono和不继承Mono的)
不继承Mono 不继承Mono代表不用挂载到场景物体上面,因此直接饿汉式 加 合并空运算符判空创建实例 >(lambda表达式)的意思是get,就是将instance赋给Instance属性 //单例private static JsonDataManager instance new JsonDataManager();public stati…...
Android 自定义Toast显示View
1、创建一个tosat显示的布局文件:toast_custom.xml <?xml version"1.0" encoding"utf-8"?> <com.hjq.shape.layout.ShapeLinearLayout xmlns:android"http://schemas.android.com/apk/res/android"android:layout_width&…...

SCRM呼叫中心高保真Axure原型 源文件分享
在数字化时代,客户关系管理(CRM)对于企业的成功至关重要。SCRM呼叫中心后台作为一款专为CRM设计的软件原型,致力于为企业提供高效、智能的客户沟通解决方案。本文将详细介绍该产品的核心功能及其对企业提升客户满意度和销售业绩的…...
Ubuntu(Linux)tcpdump使用方法详解
tcpdump命令 1.从所有网卡获取数据包 tcpdump -i any2.从指定网卡获取数据包 tcpdump -i eth03.指定网卡,IP,写文件 tcpdump -i eth0 host 192.168.16.101 -w ./tcp.dat //host 后面是发送方的地址4.指定网卡,源IP且目的IP,写入…...

Centos安装Nginx 非Docker
客户的机器属于 Centos7 系列,由于其较为陈旧,2024开始众多镜像和软件源都已失效。此篇文章将详细记录在 Centos7 操作系统上从零开始安装 Nginx 的整个流程。 本文Nginx是安装在/usr/local/nginx下 详细步骤如下: 准备Nginx安装包&#x…...

免费版的音频剪辑软件:这四款有没有你的菜?
随着音频编辑需求的日益增长,免费的音频剪辑软件逐渐成为许多创作者、学生和普通用户的心头好。今天,就让我为大家介绍几款热门的免费音频剪辑软件,并分享一下我的使用感受吧! 一、福昕音频剪辑 直通车(复制粘贴到网站…...

Facebook的隐私之战:数据保护的挑战与未来
在数字化时代,隐私保护成为了公众关注的焦点,尤其是在社交媒体巨头Facebook身上。随着用户数据泄露事件的频发,Facebook面临着日益严峻的隐私挑战。这些挑战不仅涉及法律法规的遵循,还影响着用户信任、公司声誉以及未来的发展方向…...
自定义注解和组件扫描在Spring Boot中动态注册Bean(二)
在Spring Boot中,自定义注解和组件扫描是实现动态注册Bean的两种重要手段。通过它们,开发者可以灵活地管理Spring容器中的Bean,提高开发效率和代码的可维护性。本文将详细讲解自定义注解和组件扫描在Spring Boot中如何动态注册Bean。 自定义…...
常见网络协议的介绍、使用场景及 Java 代码样例
以下是几种常见网络协议的介绍、使用场景及 Java 代码样例: 一、HTTP(HyperText Transfer Protocol,超文本传输协议) 介绍: HTTP 是用于在 Web 浏览器和 Web 服务器之间传输超文本的应用层协议。基于请求 - 响应模式…...
音视频好文总结
RTSP play同步 ffplay播放器研究分析 ffplay播放器 暂停、逐帧、音量、快进快退seek功能分析 RTSP RTP RTCP SDP基础知识 flv格式分析与解复用 TS格式详解 m3u8格式详解 FLV格式详解 MP4格式详解 HLS协议详解 RTMP协议详解 HTTP-FLV协议详解 H.264 SPS、PPS详解 H…...
云服务器磁盘满了,清理docker无用缓存、容器等清理
docker system prune 命令用于清理 Docker 系统中的各种未使用资源。根据你提供的警告信息,这条命令将会移除以下内容: 所有已停止的容器(all stopped containers) 所有未被至少一个容器使用的网络(all networks no…...

Flutter flutter_native_splash 使用指南
Flutter flutter_native_splash 使用指南 视频 https://youtu.be/dGq6LbipvXA https://www.bilibili.com/video/BV1d52tYFEzz/ 前言 原文 使用 flutter_native_splash 优化 Flutter 启动画面体验 本文详细介绍了如何在 Flutter 中使用 flutter_native_splash 插件自定义启动…...

谷歌审核放宽,恶意软件不再封号?是反垄断案影响还是开发者们的错觉
最近,谷歌因其“垄断”案而成为科技行业的焦点,这个案件可能导致谷歌业务的重大调整。同时,在Google Play上,一些开发者发现谷歌审核好像放宽了不少,这是不是与反垄断有关,谷歌应用上架或将迎来春天&#x…...
C++实现一个线程池
原文链接:C实现一个线程池 介绍 线程池是提高CPU利用率的一个非常高效的方法,线程池就是通过预先创建多个线程,当有任务时就执行,无任务时就阻塞. 相比一般的多线程方法,线程池更加简单,模块化,并且效率更高,因为不会重复创建删除线程. 预备知识 异步线程(包括f…...

为什么inet_ntoa会返回错误的IP地址?
目录 1、调用inet_addr和inet_ntoa实现整型IP与点式字符串之间的转换 1.1、调用inet_addr将点式字符串IP转换成整型IP 1.2、调用inet_ntoa将整型IP转换成点式字符串IP 2、调用inet_ntoa返回错误点式字符串IP的原因分析 3、解决多线程调用inet_ntoa返回错误点式字符串IP的办…...
编码风格之(8)C++语言规范(Google风格)3.md
编码风格之(8)C特性规范(Google风格)3 Author: Once Day Date: 2024年10月12日 一位热衷于Linux学习和开发的菜鸟,试图谱写一场冒险之旅,也许终点只是一场白日梦… 漫漫长路,有人对你微笑过嘛… 全系列文章可参考专栏: 源码分析_Once-Day的…...

华为云AI开发平台ModelArts
华为云ModelArts:重塑AI开发流程的“智能引擎”与“创新加速器”! 在人工智能浪潮席卷全球的2025年,企业拥抱AI的意愿空前高涨,但技术门槛高、流程复杂、资源投入巨大的现实,却让许多创新构想止步于实验室。数据科学家…...

深入浅出Asp.Net Core MVC应用开发系列-AspNetCore中的日志记录
ASP.NET Core 是一个跨平台的开源框架,用于在 Windows、macOS 或 Linux 上生成基于云的新式 Web 应用。 ASP.NET Core 中的日志记录 .NET 通过 ILogger API 支持高性能结构化日志记录,以帮助监视应用程序行为和诊断问题。 可以通过配置不同的记录提供程…...

【力扣数据库知识手册笔记】索引
索引 索引的优缺点 优点1. 通过创建唯一性索引,可以保证数据库表中每一行数据的唯一性。2. 可以加快数据的检索速度(创建索引的主要原因)。3. 可以加速表和表之间的连接,实现数据的参考完整性。4. 可以在查询过程中,…...

家政维修平台实战20:权限设计
目录 1 获取工人信息2 搭建工人入口3 权限判断总结 目前我们已经搭建好了基础的用户体系,主要是分成几个表,用户表我们是记录用户的基础信息,包括手机、昵称、头像。而工人和员工各有各的表。那么就有一个问题,不同的角色…...

什么是库存周转?如何用进销存系统提高库存周转率?
你可能听说过这样一句话: “利润不是赚出来的,是管出来的。” 尤其是在制造业、批发零售、电商这类“货堆成山”的行业,很多企业看着销售不错,账上却没钱、利润也不见了,一翻库存才发现: 一堆卖不动的旧货…...

CocosCreator 之 JavaScript/TypeScript和Java的相互交互
引擎版本: 3.8.1 语言: JavaScript/TypeScript、C、Java 环境:Window 参考:Java原生反射机制 您好,我是鹤九日! 回顾 在上篇文章中:CocosCreator Android项目接入UnityAds 广告SDK。 我们简单讲…...
OpenPrompt 和直接对提示词的嵌入向量进行训练有什么区别
OpenPrompt 和直接对提示词的嵌入向量进行训练有什么区别 直接训练提示词嵌入向量的核心区别 您提到的代码: prompt_embedding = initial_embedding.clone().requires_grad_(True) optimizer = torch.optim.Adam([prompt_embedding...

AirSim/Cosys-AirSim 游戏开发(四)外部固定位置监控相机
这个博客介绍了如何通过 settings.json 文件添加一个无人机外的 固定位置监控相机,因为在使用过程中发现 Airsim 对外部监控相机的描述模糊,而 Cosys-Airsim 在官方文档中没有提供外部监控相机设置,最后在源码示例中找到了,所以感…...
Kafka主题运维全指南:从基础配置到故障处理
#作者:张桐瑞 文章目录 主题日常管理1. 修改主题分区。2. 修改主题级别参数。3. 变更副本数。4. 修改主题限速。5.主题分区迁移。6. 常见主题错误处理常见错误1:主题删除失败。常见错误2:__consumer_offsets占用太多的磁盘。 主题日常管理 …...

系统掌握PyTorch:图解张量、Autograd、DataLoader、nn.Module与实战模型
本文较长,建议点赞收藏,以免遗失。更多AI大模型应用开发学习视频及资料,尽在聚客AI学院。 本文通过代码驱动的方式,系统讲解PyTorch核心概念和实战技巧,涵盖张量操作、自动微分、数据加载、模型构建和训练全流程&#…...