【30天玩转python】并发编程

news2024/9/28 1:12:53

并发编程

并发编程是指在同一时间处理多个任务的能力,任务可能是独立的,也可能是相互交错执行。并发编程的目标是充分利用 CPU 的多核处理能力,提升程序的执行效率。Python 提供了多种并发编程方法,包括多线程、多进程和异步编程。本文将介绍 Python 中的几种常见并发编程方式。


1. 多线程

多线程是一种常见的并发编程方式,它允许程序在同一进程中同时运行多个线程。Python 的 threading 模块提供了创建和管理线程的功能。

1.1 使用 threading 模块

通过 threading 模块可以轻松地创建和管理线程。下面是一个创建多线程的简单示例:

示例:创建多线程

import threading
import time

def worker(name):
    print(f"线程 {name} 开始工作")
    time.sleep(2)
    print(f"线程 {name} 结束工作")

# 创建多个线程
threads = []
for i in range(3):
    thread = threading.Thread(target=worker, args=(i,))
    threads.append(thread)
    thread.start()

# 等待所有线程完成
for thread in threads:
    thread.join()

print("所有线程完成")
1.2 线程的同步

由于线程之间是并发执行的,所以需要确保对共享数据的访问是安全的。Python 提供了 Lock(锁)机制来保证线程的同步。

示例:使用锁机制

import threading

counter = 0
lock = threading.Lock()

def increment():
    global counter
    with lock:
        for _ in range(100000):
            counter += 1

threads = []
for _ in range(2):
    thread = threading.Thread(target=increment)
    threads.append(thread)
    thread.start()

for thread in threads:
    thread.join()

print(f"计数器值为: {counter}")

在这个示例中,使用 lock 来确保多个线程不会同时修改 counter,避免竞态条件。


2. 多进程

多进程是一种并发编程方式,它通过在多个进程中运行任务来实现并发。每个进程都有自己的内存空间,因此多进程可以绕过 Python 中的全局解释器锁(GIL)限制,更适合 CPU 密集型任务。

2.1 使用 multiprocessing 模块

multiprocessing 模块用于创建和管理进程。与线程类似,进程可以并发执行任务,但进程之间的数据是独立的,无法直接共享。

示例:创建多进程

import multiprocessing
import time

def worker(name):
    print(f"进程 {name} 开始工作")
    time.sleep(2)
    print(f"进程 {name} 结束工作")

if __name__ == "__main__":
    processes = []
    for i in range(3):
        process = multiprocessing.Process(target=worker, args=(i,))
        processes.append(process)
        process.start()

    for process in processes:
        process.join()

    print("所有进程完成")
2.2 进程间通信

由于进程之间的数据是独立的,Python 提供了 QueuePipe 等机制来实现进程间通信(IPC,Inter-Process Communication)。

示例:使用 Queue 进行进程间通信

import multiprocessing

def worker(q):
    q.put("任务完成")

if __name__ == "__main__":
    queue = multiprocessing.Queue()
    process = multiprocessing.Process(target=worker, args=(queue,))
    process.start()
    process.join()

    # 从队列中获取结果
    result = queue.get()
    print(result)

在这个例子中,进程 worker 将结果放入队列中,主进程通过队列获取该结果。


3. 异步编程

异步编程是一种非阻塞的并发编程方式,适合 I/O 密集型任务。异步编程的核心思想是当一个任务等待 I/O 操作时,其他任务可以继续执行,从而避免阻塞。

3.1 使用 asyncio 模块

Python 的 asyncio 模块用于编写异步程序,通过 asyncawait 关键字定义异步函数。

示例:简单的异步函数

import asyncio

async def worker(name):
    print(f"任务 {name} 开始")
    await asyncio.sleep(2)
    print(f"任务 {name} 结束")

async def main():
    tasks = [worker(i) for i in range(3)]
    await asyncio.gather(*tasks)

# 运行异步任务
asyncio.run(main())

在这个例子中,worker 是一个异步函数,它在执行 await asyncio.sleep(2) 时不会阻塞其他任务。

3.2 异步 I/O 操作

异步编程特别适合 I/O 密集型任务,比如网络请求、文件读写等。

示例:异步网络请求

import asyncio
import aiohttp

async def fetch(url):
    async with aiohttp.ClientSession() as session:
        async with session.get(url) as response:
            return await response.text()

async def main():
    urls = ['https://example.com', 'https://example.org']
    tasks = [fetch(url) for url in urls]
    results = await asyncio.gather(*tasks)
    for result in results:
        print(result)

# 运行异步任务
asyncio.run(main())

在这个示例中,使用 aiohttp 库进行异步网络请求,实现了非阻塞的 I/O 操作。


4. 协程与生成器

Python 的生成器(generator)和协程(coroutine)也是实现并发的工具之一。协程可以通过 yield 关键字暂停和恢复函数的执行。

4.1 协程示例

协程是一种比普通生成器更高级的函数控制机制,可以通过 yield 暂停执行,再通过 send() 恢复执行。

示例:协程

def coroutine_example():
    print("启动协程")
    result = yield
    print(f"接收到的值: {result}")

co = coroutine_example()
next(co)  # 启动协程
co.send(42)  # 向协程发送值

在这个例子中,协程通过 yield 暂停执行,再通过 send() 传递数据并恢复执行。


5. 小结

并发编程在提升程序性能和响应速度方面具有重要作用。Python 提供了多种并发编程模型,包括多线程、多进程和异步编程。选择哪种模型取决于任务的特点:对于 I/O 密集型任务,异步编程是首选;对于 CPU 密集型任务,多进程可能表现更好;多线程适合轻量级的并发任务。理解并掌握这些并发编程模型,能够显著提升 Python 程序的执行效率。

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

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

相关文章

【工具分享】Chimera勒索病毒解密工具

前言 Chimera勒索软件首次出现在2015年,最初是在德国被发现。该勒索软件不仅加密受害者的文件,还威胁如果不支付赎金,就会将被盗的数据公开发布。这种“双重勒索”策略使得Chimera在众多勒索软件中脱颖而出。Chimera通常通过钓鱼邮件传播&am…

第五部分:6---信号的递达

目录 信号的递达流程: 信号在什么时候递达? 用户态和内核态: 内核态、用户态在页表的映射关系: 操作系统如何得知当前执行状态是用户态还是内核态? 操作系统如何处理被捕捉的信号? 信号的递达流程&am…

Python PyQt5 在frame中生成多个QLabel控件和彻底销毁QLabel控件

文章目录 步骤 1: 创建主窗口和布局步骤 2: 添加QLabel到QFrame步骤 3: 销毁QLabel示例代码 在PyQt5中,在QFrame或任何其他容器控件中生成多个QLabel控件并通过一个标志位或方法来彻底销毁这些QLabel控件是相对直接的操作。以下是一个简单的示例,展示了如…

爬虫小案例:爬取豆瓣网TOP250的电影信息(内含面相对象源码、及详细教学)

爬虫案例二———爬取豆瓣网TOP250的电影信息,并存入MySQL数据库 前提准备 安装pymysql库 pip install pymysql -i https://pypi.tuna.tsinghua.edu.cn/simple Python连接MySQL数据库,并进行增删改查基本操作 连接数据库 """连接MyS…

坚果N1 Air高亮版对比当贝D6X高亮版:谁是2000元预算的投影仪王者?

当贝D6X高亮版新品升级,对于那些计划在这个时间点购买投影仪的用户来说,现在是个绝佳的时机!特别是那些预算在两千元左右的,目前两千元左右的投影仪,无外乎两款产品,当贝D6X高亮版和坚果N1 Air高亮版&#…

David律所代理Beau Parsons的小狗插画图案版权维权,速排查下架

案件基本情况:起诉时间:2024-9-16案件号:2024-cv-08505原告:Beau Parsons原告律所:David起诉地:伊利诺伊州北部法院涉案商标/版权:原告品牌简介:Beau Parsons是一位来自澳大利亚的专…

AI情感陪伴新纪元:WT2605C语音芯片在成人用品中的创新应用

在探索成人用品领域的无限可能时,科技的每一次进步都为我们带来了前所未有的体验。而今,WT2605C AI语音芯片的引入,正悄然改变着这一传统行业的面貌,为成人用品赋予了全新的情感陪伴功能,开启了智能化、个性化的新时代…

鸿蒙开发(NEXT/API 12)【硬件(Pen Kit)】手写笔服务

Pen Kit(手写笔服务)是华为提供的一套手写套件,提供笔刷效果、笔迹编辑、报点预测、一笔成形和全局取色的功能。手写笔服务可以为产品带来优质手写体验,为您创造更多的手写应用场景。 目前Pen Kit提供了四种能力:手写…

Qt_网络编程

目录 1、Qt的UDP Socket 1.1 用Udp实现服务器 1.2 用Udp实现客户端 2、Qt的TCP Socket 2.1 用Tcp实现服务器 2.2 用Tcp实现客户端 3、Qt的HTTP 3.1使用Qt的HTTP 结语 前言: 网络协议是每个平台都必须遵守的,只是不同的平台所提供的网络API不…

[element-ui]记录对el-table表头样式的一些处理

1、表头换行 & 列表项换行 可用element-table组件自带的方法实现列标题换行的效果 2、小圆点样式

Codeforces Round 973 (Div. 2) A-C 题解

C 提交 MLE 了一次,原因是找到答案没加感叹号 A. Zhan’s Blender 题意 原题描述还是不太清楚 你有 n n n 个水果,每秒可以放入搅拌机 y y y 个水果,搅拌机每秒可以搅拌 x x x 个水果,问最终至少需要多少秒能搅完&#xff1…

Python的包管理工具pip安装

Python的包管理工具pip安装 一、安装步骤1.检查 pip是否已安装2.安装 pip方法一:通过 ​ensurepip​ 模块安装(推荐)方法二:通过 ​get-pip.py​ 脚本安装(经常应为网络域名问题连接不上) 3.验证pip安装4.创建别名5.更新pip 二、常…

Java网络通信—UDP

1.总揽 2.客户端 使用udp通信,需要三个东西:数据本体、通道、数据包装工具 Scanner scanner new Scanner(System.in);String string scanner.next();byte[] bytes string.getBytes();// 数据本体DatagramSocket datagramSocket new DatagramSocket(…

代码随想录冲冲冲 Day58 图论Part9

47. 参加科学大会(第六期模拟笔试) 根据昨天的dijkstra进行堆优化 使用的原因是点多但边少 所以直接对于边进行操作 1.对于priority_queue来说 这是最小堆, 小于的话就是最大堆 之后由于是根据边来说的 所以新建一个Edge并且初始化一下 之后由于使用…

动态规划入门题目->使用最小费用爬楼梯

1.题目: 2.解析: 做题模式: 步骤一:找状态转移方程 步骤二:初始化 步三:填表 步骤四:返回-> dp[n] dp[i]表示到达 i 位置最小花费 逻辑:要爬到楼顶先找到 i 位置 , 要…

深度学习:(八)深层神经网络参数与流程

深层神经网络 符号规定 L L L :表示神经网络的层数; l l l :表示第几层; n [ l ] n^{[~l~]} n[ l ] :表示第 l l l 层的节点数; a [ l ] a^{[~l~]} a[ l ] :表示第 l l l 层中的激活函数&…

【web安全】——sql注入

1.MySQL基础 1.1information_schema数据库详解 简介: 在mysql5版本以后,为了方便管理,默认定义了information_schema数据库,用来存储数据库元数据信息。schemata(数据库名)、tables(表名tableschema)、columns(列名或字段名)。…

360AI搜索上线慢思考模式:成为全球首个慢思考搜索引擎 大幅提升回答质量

近日,360 AI搜索上线“慢思考模式”,成为国内首个具备慢思考能力的AI产品、全球首个具备慢思考能力的搜索引擎。据悉,慢思考模式基于CoE 技术架构,在该模式下360AI搜索能够大幅提升回答质量,完成多数AI ChatBot无法完成…

技术成神之路:设计模式(十七)组合模式

介绍 组合模式(Composite Pattern)是一种结构型设计模式,它使你能够将对象组合成树形结构来表示“部分-整体”的层次结构。组合模式使得用户对单个对象和组合对象的使用具有一致性。 1.定义 组合模式允许将叶子对象和组合对象(容器…

猫头虎带您解决:‘vue-cli-service’ 不是内部或外部命令

猫头虎带您解决:‘vue-cli-service’ 不是内部或外部命令 🚀 今天猫头虎收到一个粉丝的提问:“猫哥,我在用 Vue 项目的时候,运行命令 npm run serve 出现了错误提示,vue-cli-service 不是内部或外部命令&a…