• Python 第三十三章 进程初识


    进程创建的两个方式

    # 开启进程的第一种方式:永远先执行主进程的代码
    
    # 多线程模块导入进程
    from multiprocessing import Process
    # 导入时间模块
    import time
    # 定义一个task函数,name函数
    def task(name):
        """
        主进程
        :param name:
        :return:
        """
        # 输出xx is running
        print(f'{name} is running')
        # 睡2秒
        time.sleep(2)
        # 输出xx is gone
        print(f'{name} is gone')
    
    # 在本模块执行此方法
    if __name__ == '__main__':
    # 在Windows环境下,开启进程必须在__name__ == '__main__'下面
    
        # 开启子进程的命令
        # 创建一个进程对象p target=task目标是task函数,args=('zs',) 给name赋值zs
        p = Process(target=task,args=('zs',)) # 元祖的形式
        # 开启一个子进程 start() 开启命令
        p.start() # 子进程会copy主进程的初始资料 相当于同时开启子进程和主进程
        # 这个信号操作系统接收到之后,会在内存中开辟一个子进程空间,然后再将主进程上所有数据copy加载到子进程,
        # 然后再去调用cpu去执行
    
        # 执行主进程
        print('主程序-开始') # 只运行主进程和子进程,先执行主进程,开辟进程会很消耗内存
        # 输出:
        # 主程序-开始
        # zsis running
        # zsis gone
        # 睡3秒
        time.sleep(3)
        print('主进程-结束')
        # 输出:
        # 主程序-开始
        # zs is running
        # zs is gone
        # 主进程-结束
    
    
    # 开启进程的第二种方式:需重构父类
    from multiprocessing import Process
    import time
    
    # 如果不进行实例化.name属性默认有传参,属性值为MyProcess1
    # 创建一个类MyProcess 继承Process
    class MyProcess(Process):
    
        # 直接实例化会报错 需要重构父类 先执行父类的run再执行自己的run
        # 实例化对象
        def __init__(self,name):
            # supper()重构父类
            super().__init__()
            # 属性值为name=属性名name
            self.name = name
    
        # 定义一个run方法 实例化
        def run(self):
            # 输出xx is running
            print(f'{self.name} is running')
            # 睡2秒
            time.sleep(2)
            # 输出xx is gone
            print(f'{self.name} is gone')
    # 在本模块执行此方法
    if __name__ == '__main__':
        # 实例化对象p 把zs给name
        p = MyProcess('zs')
        # 启动子进程
        p.start()
        print('主进程-开始')
    
    # 简单应用
    from multiprocessing import Process
    import time
    def task(name):
        print(f'{name} is running')
        time.sleep(1)
        print(f'{name} is gone')
    def task1(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone')
    def task2(name):
        print(f'{name} is running')
        time.sleep(3)
        print(f'{name} is gone')
    
    # 串行执行一个进程中执行三个任务 4.5秒
    if __name__ == '__main__':
        # 启动时间=当前时间
        start_time = time.time()
        task('zs')
        task1('zs2')
        task2('zs3')
        # 当前时间-启动时间=运行的时间
        print(f'结束时间{time.time()-start_time}')
    
        # 输出
        # zs is running
        # zs is gone
        # zs2 is running
        # zs2 is gone
        # zs3 is running
        # zs3 is gone
        # 结束时间6.009660959243774
    
    # 三个进程 并发或者并行的执行三个任务 3秒
    if __name__ == '__main__':
        start_time = time.time()
        p1 = Process(target=task,args=('zs',))
        p2 = Process(target=task1,args=('zs2',))
        p1.start()
        p2.start()
        task2('zs3')
        print(f'结束时间{time.time()-start_time}')
        # 输出
        # zs3 is running
        # zs is running
        # zs2 is running
        # zs is gone
        # zs2 is gone
        # zs3 is gone
        # 结束时间3.009711742401123
    

    进程的pid

    # 导入os模块
    import os
    # 导入time模块
    import time
    # mac 命令行获取所有的进程的pid号 ps-ef
    # Windows 命令行获取所有的进程的pid号 tasklist
    
    # 代码级别如何获取一个进程pid号 os.getpid()
    print(f'子进程:{os.getpid()}')
    # 如何获取父进程(主进程)的pid号 os.getppid()
    print(f'主进程:{os.getppid()}')
    time.sleep(5) # 睡50秒打开终端,找到Python进程的pid进行核对
    
    from multiprocessing import Process
    import time
    import os
    def task(name): # 再执行子进程
        print(f'子进程{os.getpid()}')
        print(f'主进程{os.getppid()}')
    
    if __name__ == '__main__':
        # 创建一个进程对象
        p = Process(target=task,args=('zs',))
        p.start()
        print(f'主进程的pid{os.getppid()}') # 先执行主进程
        # 输出:
        # 子进程:6712
        # 主进程:590
        # 主进程的pid590
        # 子进程6713
        # 主进程6712
    
    

    空间隔离

    # 怎么执行都是先执行主进程
    # 加个sleep睡一会
    # 空间隔离
    # 子进程修改后的name与主进程的name没有关系
    
    from multiprocessing import Process
    import os
    import time
    
    # 不可变
    name = 'zs'
    def task():
        global name
        name = 'ls'
        print(f'子进程{name}') # ls
    
    if __name__ == '__main__':
        p = Process(target=task) # 创建一个进程对象
        p.start()
        time.sleep(3)
        print(f'主进程{name}') # zs
        # 输出
        # 子进程ls
        # 主进程zs
    
    
    # 可变的
    lst = ['ww',]
    def task():
        lst.append('yy')
        print(f'子进程{lst}') # ['ww','yy']
    
    if __name__ == '__main__':
        p = Process(target=task) # 创建一个进程对象
        p.start()
        time.sleep(3)
        print(f'主进程{lst}') # ['ww']
        # 输出
        # 子进程['ww', 'yy']
        # 主进程['ww']
    

    join

    # join让主进程等待子进程的结束,再执行主进程
    from multiprocessing import Process
    import time
    
    def task(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone') # 主进程
    
    if __name__ == '__main__':
        p = Process(target=task,args=('zs',))# 创建一个进程对象
        p.start() # 启动p子进程同时启动主进程
        p.join() # 必须等待p执行完再执行主
        print('主进程')
        # 输出
        # zs is running
        # zs is gone
        # 主进程
    
    # join开启多个子进程
    # 未开启时:先执行主进程,再一个一个执行子进程(先执行时间短的)
    from multiprocessing import Process
    import time
    
    def task(name,sec):
        print(f'{name} is running')
        time.sleep(sec)
        print(f'{name} is gone') # 主进程
    
    if __name__ == '__main__':
        start_time = time.time()
        # 同一个时刻开启4个进程,并发或者并行,按照最大的时间走
        p = Process(target=task,args=('zs',2))
        p2 = Process(target=task,args=('zs2',7))
        p3 = Process(target=task,args=('zs3',5))
        p.start()
        p2.start()
        p3.start()
        print(f'主进程消耗的时间{time.time() - start_time}')  # 主进程消耗的时间与其他进程无关 0.000123秒
        # 输出:
        # 主进程消耗的时间0.0050699710845947266
        # zs is running
        # zs2 is running
        # zs3 is running
        # zs is gone
        # zs3 is gone
        # zs2 is gone
    
    # 验证1:
        # join只针对主进程,如果join下面多次join是不阻塞的
        # 不会按照一行一行输出,同时开始执行,最后执行主进程
        # 必须等待最长的1个p执行完再执行主进程
        p.join()
        print('2秒')
        p2.join()
        print('7秒')
        p3.join()
        print('5秒')
    
        print(f'主进程消耗的时间{time.time() - start_time}')  # 并发执行主进程消耗的时间 3.0387587秒
        # p1和p2和p3 同时运行 按照最长的时长打印
        # 输出
        # 主进程消耗的时间0.005324602127075195
        # zs is running
        # zs2 is running
        # zs3 is running
        # zs is gone
        # 2秒
        # zs3 is gone
        # zs2 is gone
        # 7秒
        # 5秒
        # 主进程消耗的时间7.008730888366699
    
    
    
    # 验证2
    # 对验证1进行优化代码  循环打印
    
    # 正确示范
    from multiprocessing import Process
    import time
    def task(sec):
        print(f'is running')
        time.sleep(sec)
        print(f'is gone')
    
    if __name__ == '__main__':
        start_time = time.time()
        l1 = []
        for i in range(1,4):
            p = Process(target=task,args=(i,))
            l1.append(p)
            p.start()
    
        for i in l1:
            i.join()
    
        print(f'主进程{time.time()-start_time}')
    
    
    # join就是阻塞,主进程有join主进程下面的代码一律不执行
    

    进程的其他参数

    from multiprocessing import Process
    import time
    
    
    # 杀死子进程 terminate()
    def task(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone')
    
    if __name__ == '__main__':
        p = Process(target=task,args=('zs',)) # 创建一个进程对象
        p.start() # 启动进程
        p.terminate() # 杀死子进程
        print('主进程')
        # 输出
        # 主进程
    # 只输出主进程,子进程被杀死
    
    from multiprocessing import Process
    import time
    
    def task(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone')
    
    
    if __name__ == '__main__':
        p = Process(target=task, args=('zs',)) # 创建一个进程对象
        p.start() # 启动进程
        time.sleep(1) # 睡1秒
        p.terminate()  # 杀死子进程
        print('主进程')
        # 输出
        # zs is running
        # 主进程
    # 先执行子进程睡一会,再杀死子进程,最后执行子进程
    
    # 查看是否真的杀死子进程 子进程是否还活着is_alive()方法
    from multiprocessing import Process
    import time
    
    def task(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone')
    
    if __name__ == '__main__':
        p = Process(target=task,args=('zs',)) # 创建一个进程对象
        p.start() # 启动子进程
        p.terminate() # 杀死子进程
        p.join() # 阻塞 还可以用sleep()
        print(p.is_alive()) # 判断子进程是否还活着 True活着 False死了
        print('主进程')
        # 输出
        # False
        # 主进程
    
    
    # 增加属性 默认name属性 Process属性值
    from multiprocessing import Process
    import time
    
    def task(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone')
    
    if __name__ == '__main__':
        p = Process(target=task,args=('zs',),name ='alex') # 创建一个进程对象
        p.start() # 启动子进程
        p.name = 'ls' # 添加属性
        print(p.name) # 打印name :ls
        print('主进程')
        # 输出:ls
        # 主进程
        # zs is running
        # zs is gone
    

    守护进程

    # 守护进程
    # 子进程守护者主进程,只要主进程结束,子进程跟着结束 daemon=True
    from multiprocessing import Process
    import time
    
    def task(name):
        print(f'{name} is running')
        time.sleep(2)
        print(f'{name} is gone')
    
    if __name__ == '__main__':
        p = Process(target=task,args=('zs',)) # 创建一个进程对象p
        # 将p子进程设置成守护进程,只要主进程结束,守护进程马上结束
        p.daemon = True # 在开启子进程之前设置守护进程
        p.start()# 开启子进程
        time.sleep(1) # 睡一会
        print('主进程')
        # 输出
        # zs is running
        # 主进程
    
  • 相关阅读:
    学习计划(一)——JavaScript 殷的博客
    学习计划——巩固基础+进阶练习 殷的博客
    第二章:在HTML中使用JavaScript 殷的博客
    W3Cschool学习笔记——CSS教程 殷的博客
    W3Cschool学习笔记——HTML5基础教程 殷的博客
    PS切图篇(一)界面设置 殷的博客
    W3Cschool学习笔记——CSS3教程 殷的博客
    PHP Parse error: syntax error, unexpected T_ENCAPSED_AND_WHITESPACE, expecting T_STRING or T_VARIABLE or T_NUM_STRING
    css怎么让图片垂直左右居中?(外层div是浮动且按照百分比排列)
    在各浏览器和各分辨率下如何让div内的table垂直水平居中?
  • 原文地址:https://www.cnblogs.com/zhangshan33/p/11384741.html
Copyright © 2020-2023  润新知