python 多線程與多進(jìn)程效率測試
1、概述
在Python中,計(jì)算密集型任務(wù)適用于多進(jìn)程,IO密集型任務(wù)適用于多線程
正常來講,多線程要比多進(jìn)程效率更高,因?yàn)檫M(jìn)程間的切換需要的資源和開銷更大,而線程相對(duì)更小,但是我們使用的Python大多數(shù)的解釋器是Cpython,眾所周知Cpython有個(gè)GIL鎖,導(dǎo)致執(zhí)行計(jì)算密集型任務(wù)時(shí)多線程實(shí)際只能是單線程,而且由于線程之間切換的開銷導(dǎo)致多線程往往比實(shí)際的單線程還要慢,所以在 python 中計(jì)算密集型任務(wù)通常使用多進(jìn)程,因?yàn)楦鱾€(gè)進(jìn)程有各自獨(dú)立的GIL,互不干擾。
而在IO密集型任務(wù)中,CPU時(shí)常處于等待狀態(tài),操作系統(tǒng)需要頻繁與外界環(huán)境進(jìn)行交互,如讀寫文件,在網(wǎng)絡(luò)間通信等。在這期間GIL會(huì)被釋放,因而就可以使用真正的多線程。
上面都是理論,接下來實(shí)戰(zhàn)看看實(shí)際效果是否符合理論
2、代碼練習(xí)
"""多線程多進(jìn)程模擬執(zhí)行效率"""
from multiprocessing import Pool
from threading import Thread
import time, math
def simulation_IO(a):
"""模擬IO操作"""
time.sleep(3)
def simulation_compute(a):
"""模擬計(jì)算密集型任務(wù)"""
for i in range(int(1e7)):
math.sin(40) + math.cos(40)
return
def normal_func(func):
"""普通方法執(zhí)行效率"""
for i in range(6):
func(i)
return
def mp(func):
"""進(jìn)程池中的map方法"""
with Pool(processes=6) as p:
res = p.map(func, list(range(6)))
return
def asy(func):
"""進(jìn)程池中的異步執(zhí)行"""
with Pool(processes=6) as p:
result = []
for j in range(6):
a = p.apply_async(func, args=(j, ))
result.append(a)
res = [j.get() for j in result]
def thread(func):
"""多線程方法"""
threads = []
for j in range(6):
t = Thread(target=func, args=(j, ))
threads.append(t)
t.start()
for t in threads:
t.join()
def showtime(f, func, name):
"""
計(jì)算并展示函數(shù)的運(yùn)行時(shí)間
:param f: 多進(jìn)程和多線程的方法
:param func: 多進(jìn)程和多線程方法中需要傳入的函數(shù)
:param name: 方法的名字
:return:
"""
start_time = time.time()
f(func)
print(f"{name} time: {time.time() - start_time:.4f}s")
def main(func):
"""
運(yùn)行程序的主函數(shù)
:param func: 傳入需要計(jì)算時(shí)間的函數(shù)名
"""
showtime(normal_func, func, "normal")
print()
print("------ 多進(jìn)程 ------")
showtime(mp, func, "map")
showtime(asy, func, "async")
print()
print("----- 多線程 -----")
showtime(thread, func, "thread")
if __name__ == "__main__":
print("------------ 計(jì)算密集型 ------------")
func = simulation_compute
main(func)
print()
print()
print()
print("------------ IO 密集型 ------------")
func = simulation_IO
main(func)
3、運(yùn)行結(jié)果

| 線性執(zhí)行 | 多進(jìn)程(map) | 多進(jìn)程(async) | 多線程 | |
|---|---|---|---|---|
| 計(jì)算密集型 | 16.0284s | 3.5236s | 3.4367s | 15.2142s |
| IO密集型 | 18.0201s | 3.0945s | 3.0809s | 3.0041s |
從表格中很明顯的可以看出:
- 計(jì)算密集型任務(wù)的速度:多進(jìn)程 >多線程> 單進(jìn)程/線程
- IO密集型任務(wù)速度: 多線程 > 多進(jìn)程 > 單進(jìn)程/線程。
所以,針對(duì)計(jì)算密集型任務(wù)使用多進(jìn)程,針對(duì)IO密集型任務(wù)使用多線程
到此這篇關(guān)于python 多線程與多進(jìn)程效率測試 的文章就介紹到這了,更多相關(guān)python 多線程內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
python常見統(tǒng)計(jì)分析處理函數(shù)解讀
這篇文章主要介紹了python常見統(tǒng)計(jì)分析處理函數(shù),具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-07-07
詳解從Django Rest Framework響應(yīng)中刪除空字段
這篇文章主要介紹了詳解從Django Rest Framework響應(yīng)中刪除空字段,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2019-01-01
Python調(diào)用DeepSeek API查詢ClickHouse的流程步驟
本文介紹如何利用DeepSeek API和ClickHouse構(gòu)建自然語言查詢數(shù)據(jù)庫,文章詳細(xì)說明了環(huán)境配置步驟,包括Python安裝、必備庫安裝、DeepSeek API Key獲取和ClickHouse連接配置,需要的朋友可以參考下2026-03-03

