zoukankan      html  css  js  c++  java
  • python高级线程、进程和进程池

     
    Python提供两个模块进行多线程的操作,分别是thread和threading,
    前者是比较低级的模块,用于更底层的操作,一般应用级别的开发不常用。
    方法1:直接使用threading.Thread()
    import threading
     
    # 这个函数名可随便定义
    def run(n):
        print("current task:", n)
     
    if __name__ == "__main__":
        t1 = threading.Thread(target=run, args=("thread 1",))
        t2 = threading.Thread(target=run, args=("thread 2",))
        t1.start()
        t2.start()
     
    方法2:继承threading.Thread来自定义线程类,重写run方法
    import threading
     
    class MyThread(threading.Thread):
        def __init__(self, n):
            super(MyThread, self).__init__()  # 重构run函数必须要写
            self.n = n
     
        def run(self):
            print("current task:", self.n)
     
    if __name__ == "__main__":
        t1 = MyThread("thread 1")
        t2 = MyThread("thread 2")
     
        t1.start()
        t2.start()

    二、创建多进程

    Python 要进行多进程操作,需要用到muiltprocessing库,其中的Process类跟threading模块的Thread类很相似。所以直接看代码熟悉多进程。
    方法1:直接使用Process, 代码如下:
    from multiprocessing import Process  
     
    def show(name):
        print("Process name is " + name)
     
    if __name__ == "__main__":
        proc = Process(target=show, args=('subprocess',))  
        proc.start()  
        proc.join()
    方法2:继承Process来自定义进程类,重写run方法, 代码如下:
    from multiprocessing import Process
    import time
     
    class MyProcess(Process):
        def __init__(self, name):
            super(MyProcess, self).__init__()
            self.name = name
     
        def run(self):
            print('process name :' + self.name)
            time.sleep(1)
     
    if __name__ == '__main__':
        for i in range(3):
            p = MyProcess(str(i))
            p.start()
        for i in range(3):
            p.join()
    多进程通信
    进程之间不共享数据的。如果进程之间需要进行通信,则要用到Queue模块或者Pipi模块来实现。
    Queue
    Queue 是多进程安全的队列,可以实现多进程之间的数据传递。它主要有两个函数,put和get。
    put() 用以插入数据到队列中,put 还有两个可选参数:blocked 和 timeout。如果 blocked 为 True(默认值),并且 timeout 为正值,该方法会阻塞 timeout 指定的时间,直到该队列有剩余的空间。如果超时,会抛出 Queue.Full 异常。如果 blocked 为 False,但该 Queue 已满,会立即抛出 Queue.Full 异常。
    get()可以从队列读取并且删除一个元素。同样,get 有两个可选参数:blocked 和 timeout。如果 blocked 为 True(默认值),并且 timeout 为正值,那么在等待时间内没有取到任何元素,会抛出 Queue.Empty 异常。如果blocked 为 False,有两种情况存在,如果 Queue 有一个值可用,则立即返回该值,否则,如果队列为空,则立即抛出 Queue.Empty 异常。
    具体用法如下:
    from multiprocessing import Process, Queue
    def put(queue):
        queue.put('Queue 用法')
    if __name__ == '__main__':
        queue = Queue()
        pro = Process(target=put, args=(queue,))
        pro.start()
        print(queue.get())   
        pro.join()
    三、进程池
    创建多个进程,我们不用傻傻地一个个去创建。我们可以使用Pool模块来搞定。
    Pool 常用的方法如下:
    方法 含义
    apply() 同步执行(串行)
    apply_async() 异步执行(并行)
    terminate() 立刻关闭进程池
    join() 主进程等待所有子进程执行完毕。必须在close或terminate()之后使用
    close() 等待所有进程结束后,才关闭进程池
     
    具体用法见示例代码:
    from multiprocessing import Pool
    def show(num):
        print('num : ' + str(num))
     
     
    if __name__=="__main__":
        pool = Pool(processes = 3)
        for i in range(6):
            # 维持执行的进程总数为processes,当一个进程执行完毕后会添加新的进程进去
            pool.apply_async(show, args=(i, ))       
        print('======  apply_async  ======')
        pool.close()
        #调用join之前,先调用close函数,否则会出错。执行完close后不会有新的进程加入到pool,join函数等待所有子进程结束
        pool.join()
     
     
     
     
     
     
     
     
     
     
     
     

  • 相关阅读:
    linux-centos7安装mysql5.6
    CentOS Linux 7.2相关配置 以及环境搭建
    centos中查找占用磁盘大文件
    记录Redis在Windows下的安装与服务管理报错:Redis service failed to start.
    Spring cloud ----- 服务治理
    Spring Cloud技术分析
    Linux常用命令总结
    Java面试题总结(不断更新中)
    SpringBoot几种定时任务的实现方式
    Java 定时任务---Timer
  • 原文地址:https://www.cnblogs.com/sea-stream/p/14193400.html
Copyright © 2011-2022 走看看