一、基本概念

  • 定义:运行中的程序

  • 程序和进程之间的区别:

    • 程序只是一个文件

    • 进程是这个文件被CPU运行起来了

  • 进程是计算机中最小的资源分配单位

  • 在操作系统中的唯一标识符 :pid

  • 进程调度:

    • 操作系统调度进程的算法

      • 短作业优先算法

      • 先来先服务算法

      • 时间片轮转算法

      • 多级反馈算法

  • 并行与并发

    • 并行

      • 两个程序 两个CPU 每个程序分别占用一个CPU自己执行自己的

      • 看起来是同时执行,实际在每一个时间点上都在各自执行着

    • 并发

      • 两个程序 一个cpu 每个程序交替的在一个cpu上执行

      • 看起来在同时执行,但是实际上仍然是串行

  • 同步 / 异步 / 阻塞 / 非阻塞

    • 同步:一个任务的完成需要依赖另外一个任务时,只有等待被依赖的任务完成后,依赖的任务才能算完成,这是一种可靠的任务序列,要么成功都成功,失败都失败,两个任务的状态可以保持一致

    • 异步:不需要等待被依赖的任务完成,只是通知被依赖的任务要完成什么工作,依赖的任务也立即执行,只要自己完成了整个任务就算完成了,至于被依赖的任务最终是否真正完成,依赖它的任务无法确定,所以它是不可靠的任务序列

    • 阻塞:cpu不工作

    • 非阻塞:cpu工作

    • 同步阻塞

      • conn.recv

      • socket 阻塞的tcp协议的时候

    • 同步非阻塞

      • func() 没有io操作

      • socket 非阻塞的tcp协议的时候

      • 调用函数(这个函数内部不存在io操作)

    • 异步非阻塞

      • 把func扔到其他任务里去执行了

      • 我本身的任务和func任务各自执行各自的 没有io操作

    • 异步阻塞

  • 进程的三状态

    • 就绪(Ready)状态

      • 当进程已分配到除CPU以外的所有必要的资源,只要获得处理机便立即执行,这时的进程状态称为就绪状态

    • 执行/运行(Running)

      • 状态当进程已获得处理机,其程序正在处理机上执行,此时的进程状态称为执行状态

    • 阻塞(Blocked)状态

      • 正在执行的进程,由于等待某个事件发生而无法执行时,便放弃处理机而处于阻塞状态。引起进程阻塞的事件可有多种,例如,等待I/O完成、申请缓冲区不能满足、等待信件(信号)等

  • 子进程 / 父进程

    • 在父进程中创建子进程

      • 在pycharm中启动的所有py程序都是pycharm的子进程

    • os模块

      • os.getpid():获取子进程的pid

      • os.getppid():获取父进程的pid

二、进程模块

  • 开启进程

    # 面向函数方式:
    import os
    import time
    from multiprocessing import Process
    ​
    def eat():
        print('start eating',os.getpid())
        time.sleep(1)
        print('end eating',os.getpid())
    ​
    def sleep():
        print('start sleeping',os.getpid())
        time.sleep(1)
        print('end sleeping',os.getpid())
    ​
    if __name__ == '__main__':
        p1 = Process(target=eat)    # 创建一个即将要执行eat函数的进程对象
        p1.start()                  # 异步 调用开启进程的方法 但是并不等待这个进程真的开启
        p2 = Process(target=sleep)  # 创建一个即将要执行sleep函数的进程对象
        p2.start()                  # 异步 调用开启进程的方法 但是并不等待这个进程真的开启
        print('main :',os.getpid())
    # 面向对象方式:
    import os
    import time
    from multiprocessing import Process
    ​
    class MyProcecss1(Process):
        def __init__(self,x,y):
            self.x = x
            self.y = y
            super().__init__()
        def run(self):
            print(self.x,self.y,os.getpid())
            for i in range(5):
                print('in son2')
    ​
    if __name__ == '__main__':
        mp = MyProcecss1(1,2)
        mp.daemon = True
        mp.start()
        print(mp.is_alive())
        time.sleep(1)
        mp.terminate()
  • 操作系统创建进程的方式不同

    • windows操作系统执行开启进程的代码

      • 实际上新的子进程需要通过import父进程的代码来完成数据的导入工作

      • 所以有一些内容我们只希望在父进程中完成,就写在if name == 'main':下面

    • ios linux操作系统创建进程 fork

  • 主进程和子进程之间的关系

    • 主进程的结束逻辑

      • 主进程的代码结束

      • 所有的子进程结束

      • 给子进程回收资源

      • 主进程结束

    import os
    import time
    from multiprocessing import Process
    def func():
        print('start',os.getpid())
        time.sleep(10)
        print('end',os.getpid())
    ​
    if __name__ == '__main__':
        p = Process(target=func)
        p.start()   # 异步 调用开启进程的方法 但是并不等待这个进程真的开启
        print('main :',os.getpid())
        # 主进程没结束 :等待子进程结束
        # 主进程负责回收子进程的资源
        # 如果子进程执行结束,父进程没有回收资源,那么这个子进程会变成一个僵尸进程
    示例

相关文章: