Python语言之并发编程

目录

(一)_thread模块实现多线程(已不推荐使用)

  • 没有控制进程结束机制
  • 只有一个同步原语(锁)
import time
import _thread


def work(n):
    print('当前时间开始为:{}'.format(time.ctime()))
    time.sleep(n)
    print('当前时间结束为为:{}'.format(time.ctime()))


def main():
    print('当前时间为:{}'.format(time.ctime()))
    _thread.start_new_thread(work,(4,))
    _thread.start_new_thread(work,(2,))
    time.sleep(6)
    print('当前时间结束为:{}'.format(time.ctime()))


if __name__ == '__main__':
    main()

(二)threading模块

threading.Thread

import time
import threading

def work(n):
    print('当前时间开始为:{}'.format(time.ctime()))
    time.sleep(n)
    print('当前时间结束为为:{}'.format(time.ctime()))


def main():
    print('main开始为:{}'.format(time.ctime()))
    threads = []
    t1 = threading.Thread(target=work,args=(4,))
    t2 = threading.Thread(target=work,args=(2,))
    threads.append(t1)
    threads.append(t2)
    for t in threads:
        t.start()
    print('main结束为:{}'.format(time.ctime()))


if __name__ == '__main__':
    main()
------------------------------------------------------------------------------
main开始为:Tue Jan 14 21:33:42 2020
当前时间开始为:Tue Jan 14 21:33:42 2020
当前时间开始为:Tue Jan 14 21:33:42 2020
main结束为:Tue Jan 14 21:33:42 2020
当前时间结束为为:Tue Jan 14 21:33:44 2020
当前时间结束为为:Tue Jan 14 21:33:46 2020

join()让主线程等待

import threading

def work(n):
    print('当前时间开始为:{}'.format(time.ctime()))
    time.sleep(n)
    print('当前时间结束为为:{}'.format(time.ctime()))


def main():
    print('main开始为:{}'.format(time.ctime()))
    threads = []
    t1 = threading.Thread(target=work,args=(4,))
    t2 = threading.Thread(target=work,args=(2,))
    threads.append(t1)
    threads.append(t2)
    for t in threads:
        t.start()
    for t in threads:
        t.join()
    print('main结束为:{}'.format(time.ctime()))


if __name__ == '__main__':
    main()
-----------------------------------------------------------------
main开始为:Tue Jan 14 21:36:57 2020
当前时间开始为:Tue Jan 14 21:36:57 2020
当前时间开始为:Tue Jan 14 21:36:57 2020
当前时间结束为为:Tue Jan 14 21:36:59 2020
当前时间结束为为:Tue Jan 14 21:37:01 2020
main结束为:Tue Jan 14 21:37:01 2020

自定义Mythread

import time
import threading


class MyThread(threading.Thread):
    def __init__(self,func,args):
        threading.Thread.__init__(self)
        self.func = func
        self.args = args

    def run(self):
        self.func(*self.args)


def work(n):
    print('当前时间开始为:{}'.format(time.ctime()))
    time.sleep(n)
    print('当前时间结束为为:{}'.format(time.ctime()))


def main():
    print('main开始为:{}'.format(time.ctime()))
    threads = []
    t1 = MyThread(work,(4,))
    threads.append(t1)
    t2 = MyThread(work,(4,))
    threads.append(t2)
    for t in threads:
        t.start()
    for t in threads:
        t.join()
    print('main结束为:{}'.format(time.ctime()))


if __name__ == '__main__':
    main()

(三)锁

threading.Lock()

import threading
import time
import random

eggs = []
lock1 = threading.Lock()


def put_egg(n,list):
    lock1.acquire()
    for i in range(1,n+1):
        time.sleep(random.randint(0,2))
        list.append(i)
    lock1.release()


def main():
    threads = []
    t1 = threading.Thread(target=put_egg,args=(5,eggs))
    threads.append(t1)
    t2 = threading.Thread(target=put_egg,args=(5,eggs))
    threads.append(t2)
    for t in threads:
        t.start()
    for t in threads:
        t.join()
    print(eggs)


if __name__ == '__main__':
    main()
-------------------------------------------------------------
[1, 2, 3, 4, 5, 1, 2, 3, 4, 5]

with语法

def put_egg(n,list):
    with lock1:
        for i in range(1, n + 1):
            time.sleep(random.randint(0, 2))
            list.append(i)

(四)队列

  • Queue FIFO
  • LifoQueue LIFO
  • PriorityQueue 优先队列
import threading
import queue
import time
import random


def producer(data_queue):
    for i in range(5):
        time.sleep(0.5)
        item = random.randint(0, 100)
        data_queue.put(item)
        print(f'{threading.current_thread().name}在队列中放入数据项{item}')


def consumer(data_queue):
    while True:
        try:
            item = data_queue.get(timeout=3)
            print(f'{threading.current_thread().name}在队列中移除了数据项{item}')
        except queue.Empty:
            break
        else:
            data_queue.task_done()


def main():
    q = queue.Queue()
    threads = []
    producer1 = threading.Thread(target=producer, args=(q,))
    producer1.start()
    for i in range(2):
        c = threading.Thread(target=consumer, args=(q,))
        threads.append(c)
    for t in threads:
        t.start()
    for t in threads:
        t.join()
    #队列所有项处理完毕前阻塞
    q.join()


if __name__ == '__main__':
    main()

(五)多进程模块

IO密集型采用多线程,cpu密集型可采用多进程

import time
import multiprocessing


def fun(n):
    print(f'{multiprocessing.current_process().name} 执行开始于:{time.ctime()}')
    time.sleep(n)
    print(f'{multiprocessing.current_process().name} 执行结束于:{time.ctime()}')


def main():
    print(f'主函数运行于:{time.ctime()}')
    processes = []
    p1 = multiprocessing.Process(target=fun,args=(4,))
    processes.append(p1)

    p2 = multiprocessing.Process(target=fun,args=(4,))
    processes.append(p2)

    for i in processes:
        i.start()

    for i in processes:
        i.join()

    print(f'主函数结束于:{time.ctime()}')


if __name__ == '__main__':
    main()

(六)concurrent.futures模块

  1. ThreadPoolExecutor 多线程
  2. ProcessPoolExecutor 多进程
import concurrent.futures


def work(i):
    print(i)


def fun1():
    with concurrent.futures.ThreadPoolExecutor(max_workers=5) as executor:
        executor.submit(work, 5)


def fun2():
    with concurrent.futures.ProcessPoolExecutor(max_workers=5) as executor:
        executor.submit(work, 5)
上一篇:python学习笔记(32)多线程&多进程


下一篇:threading多线程模块