多进程与多线程的原理以及 池与锁的应用

  • 多进程
    • os.fork() 进程
      • 进程的创建
        • fork创建子进程, 返回值0 代表创建子进程后的返回值且返回值必须是0.防止 循环创建导致死循环( 这是系统机制)
          • fork创建子进程

            多进程与多线程的原理以及 池与锁的应用

      • form multiprocessing import process
        • 参数列表
          • target: 表示这个进程实列所调用的对象 指你要对谁进行子进程操作
          • arge : 调用对象的位置参数元祖 放实参的地方,对象要用形参进行接收
          • kwargs: 放关键字参数 键值对 要以**关键字形参进行接收
          • name 当前子进程的名字
    • Process 创建子进程
      • 子进程就是将主进程内的程序分配给子进程进行异步执行

        多进程与多线程的原理以及 池与锁的应用

      • 子进程和可以多个创建
        • 多进程与多线程的原理以及 池与锁的应用

      • join 创建等待时间 is_alive() 检测进程程序是否存在返回值为布尔值
        • terminate 清除程序

          多进程与多线程的原理以及 池与锁的应用

        •  
      • 自定义类创建子进程
        • 继承Process

          多进程与多线程的原理以及 池与锁的应用

    • Pool 进程池的创建
      • Process创建数量不多时使用,而Pool是批量成千上百的创建子进程的一个方法 由multiprocessing模块提供Pool方法
      • Pool() 可以添加创建次数指定最大创建进程数量, 如果创建进程数大于进程池限制个数则会等待,一直到Pool()进程池里有进程结束时才会往里添加新的进程来执行

        多进程与多线程的原理以及 池与锁的应用

      • apply方法是阻塞的。
        • 意思就是等待当前子进程执行完毕后,在执行下一个进程。

          多进程与多线程的原理以及 池与锁的应用

      • apply_async 是异步非阻塞的。
        • 意思就是:不用等待当前进程执行完毕,随时根据系统调度来进行进程切换
        • 首先主进程开始运行,碰到子进程后,主进程说:让我先运行个够,等到操作系统进行进程切换的时候,在交给子进程运行。以为我们的程序太短,然而还没等到操作系统进行进程切换,主进程就运行完毕了。
          • 多进程与多线程的原理以及 池与锁的应用

      • apply_async 加join() 也可以进行同步操作
        • 想要子进程执行,就告诉主进程:你等着所有子进程执行完毕后,在运行剩余部分

          多进程与多线程的原理以及 池与锁的应用

    • Queue 进程通讯
      • 进程与进程本身是相互独立的没有任何关系,当需要两个进程进行交互通信
        • Queue()对象(q = Queue()),若括号中没有指定最大接受的消息或者为负值代替,那么就代表接受的消息数量没有限制无上限.
        • Queue.qsize() : 返回当前队列包含的消息数量
        • Queue.empty() 如果队列为空,返回值为True,反之有消息,返回值为False;
        • Queue.full() 如果队列消息满 返回True, 没满返回False
        • Queue.get([block[],timeout]) 获取队列中的一条消息,然后在消息在通讯里进行移出 只获取单条
          • block = True
            • 且没有设置timeout(单位秒),消息列队如果为空,此时程序将被阻塞(停在读取状态),直到从消息列队读到消息为止,如果设置了timeout,则会等待timeout秒,若还没读取到任何消息,则抛出"Queue.Empty"异常;
          • block = False
            • 如果block值为False,消息列队如果为空,则会立刻抛出"Queue.Empty"异常
        • Queue.put_nowait() 不会等待队列有空闲位置再放入数据,如果数据放入不成功就直接崩溃 (暴力添加)
        • Queue.get_nowait() 队列为空,取值的时候不等待,但是取不到值那么直接崩溃了
      • Process() 创建进程 Queue的put和get应用

        多进程与多线程的原理以及 池与锁的应用

      • 进程通讯Queue

        多进程与多线程的原理以及 池与锁的应用

      • 进程池Pool中 Queue用法
        • 如果要使用Pool创建进程,就需要使用multiprocessing.Manager()中的Queue(),而不是multiprocessing.Queue(),否则会得到一条如下的错误信息:
        • RuntimeError: Queue objects should only be shared between processes through inheritance.

          多进程与多线程的原理以及 池与锁的应用

        •  
  • 多线程
    • threading模块里的Thread创建线程
      • 启动一个线程就是把一个函数传入并创建Thread实例,然后调用start()开始执行:

        多进程与多线程的原理以及 池与锁的应用

      • enumerate() 查看当前线程数量 默认下线程为1 主进程里默认有一个线程 返回值为int类型

        多进程与多线程的原理以及 池与锁的应用

      • 自定义创建多线程-继承Thread

        多进程与多线程的原理以及 池与锁的应用

    • 多线程全局变量

      多进程与多线程的原理以及 池与锁的应用

    • 多线程锁的应用

      多进程与多线程的原理以及 池与锁的应用

    • # 创建锁 mutex=threading.Lock()
    • # 上锁 mutex.acquire()
    • # 开锁 mutex.release()
    • 其中,锁定方法acquire可以有一个blocking参数。 如果设定blocking为True,则当前线程会堵塞,直到获取到这个锁为止(如果没有指定,那么默认为True) 如果设定blocking为False,则当前线程不会堵塞