初学者

Python多进程和多线程

2019-11-13  本文已影响0人  陈忠俊

Python是跨平台的动态语言,自然是支持多线程和多进程的。其多进程是模仿多线程开发出来的。
进程,是一个程序在某个数据集合上的运行活动。比如,你用QQ音影打开了一部电影,这个时候就启动了一个进程。
线程,是程序的最小执行单元,线程属于进程。一个进程可以启动多个线程,反之不成立。
查看当前CPU的核心数:

>>> from os import cpu_count
>>> cpu_count()
8

上面给的是逻辑核心,现在好一点的处理器都是支持超线程技术,物理核心是4个。
尝试启动一个进程:

from multiprocessing import Process
import time

def func(args):
    for i in args:
        print(i)
        time.sleep(1)

if __name__ == '__main__':
    p = Process(target = func, args = ([1,3,5,7,9],)) #创建一个进程
    p.start() #启动子进程
    p.join() #等待子进程结束
    print("Done")

也可以通过进程池的方式一次启动多个进程:

from multiprocessing import Pool
import time
import random
import os

def func(id):
    print("run task: ", id)
    time.sleep(random.random() * 10)
    print("task done: ", id)

if __name__ == '__main__':
    thread_num = os.cpu_count() # 获取cpu逻辑核心数
    p = Pool(thread_num) # 创建进程池
    for i in range(thread_num + 1): # 创建比CPU逻辑核心数+1个进程,可以看到一个进程在等待
        p.apply_async(func, args = (i,))
    p.close()
    p.join()
    print("Done")

输出结果:

run task:  0
run task:  1
run task:  2
...
run task:  6
run task:  7
task done:  2
run task:  8 # 该进程 在进程-2运行完成之后再启动 
task done:  1

创建进程池p = Pool(),这里papplyapply_async两个方法,其一是同步,第二个是异步。
同步,可以理解为单行道汽车过红绿灯,前面的车没过去,后面的车只能等待。
异步,可以理解为多车道的车过绿灯,每辆车在绿灯的情况下,按自己的情况开走,不用等待其他车道的车。

Python多进程会利用多核的优势,但是在多任务调度过程中,又会消耗大量的cpu资源。这个要看具体的任务。
由于GIL的存在,Python在多线程情景中,对于IO的任务,多线程会加快运行速度,而对于计算密集型的任务,多线程将不适合。

from threading import Thread
import random
import time
class MyThread(Thread):
    def __init__(self, threadId, **kwargs):
        super().__init__()
        self.threadId = threadId
        self.dic = kwargs
        self.start() # 创建新的线程时就启动该线程

    def run(self):
        print("Start thread: ", self.threadId)
        test(self.dic)
        time.sleep(random.random() * 5)
        print("Thread: %s done" %self.threadId)
        
def test(kwargs):
    for i in kwargs:
        print("%s: %s" %(i, kwargs[i]))

if __name__ == "__main__":
    threads = []
    for i in range(3):
        threads.append(MyThread(i, name = 'eclipse', age = 30))
    for th in threads:
        th.join() #等待所以线程结束

输出:

Start thread:  0
name: eclipse
age: 30
Start thread:  2
name: eclipse
Start thread:  1
age: 30
name: eclipse
age: 30
Thread: 0 done
Thread: 1 done
Thread: 2 done
All threads done!
上一篇 下一篇

猜你喜欢

热点阅读