python之路---并发编程之进程&进程对象相关的属性或方法

join()

import time
from multiprocessing import Process
x = 1


def task(name, num):
    print('%s is running' % name)
    global x
    x = 0
    time.sleep(num)
    print('%s is done' % name)


if __name__ == '__main__':
    obj_list = []
    start_time = time.time()
    for i in range(1, 3):
        obj = Process(target=task, args=('子进程%s' % i, i))
        obj_list.append(obj)
        obj.start()
    for obj in obj_list:
        obj.join()
# join()让父进程原地等待,等子进程运行完毕后,才执行下一行代码(也拥有wait方法,等子进程运行完毕后,向操作系统发送请求,回收子进程占用的PID)

    end_start = time.time()
    print(x, end_start - start_time)

# 可以看出修改子进程内的变量值并不会影响到父进程--->进程之间内存空间彼此隔离

 一个例子

import time
from multiprocessing import Process


def task(name):
    print('%s is running'% name)
    time.sleep(15) # 给我们在cmd内查看进程预留时间


if __name__ == '__main__':
    p = Process(target=task,args=('进程一',))
    p.start()
    print(p.pid)
    p.join()
    print(p.pid)

# 执行结果
26324
进程一 is running
26324

说join()内也拥有wait()方法,会在子进程结束后向操作系统发送请求,回收子进程的pid,那么为什么在join()之后仍然能查到子进程的pid?

join()确实向操作系统发送了请求,操作系统也确实回收了子进程(通过cmd可以查看到),但是在子进程被创建时,pid已经成为父进程的一个属性(指向子进程的pid),join之后我们并没有删除这个属性(只是这个属性没有任何意义)

 os.get_pid与os.get_ppid()

import time,os
from multiprocessing import Process


def task(name):
    print('%s is running'% name)
    print(os.getpid())
    time.sleep(5)


if __name__ == '__main__':
    p = Process(target=task,args=('进程一',))
    p.start()
    p.join()
    print(os.getpid(),os.getppid())
    time.sleep(100)

我们可以用os模块下的get_pid()查看当前进程的pid,以及get_ppid()查看父进程的pid

通过cmd可以看出子进程与父进程的pid都是指向python.exe,而父进程的父进程是pycharm

原因是子进程与父进程执行的都是python代码,需要通过解释器执行(将所要执行的代码作为参数传入解释器内),我们的进程是在pychram内执行的,如果通过cmd执行那么父进程就是cmd.exe

我们通过cmd执行这个py文件然后用另一个cmd2去杀死cmd1,发现cmd1并没有关闭

原因是子进程在占用cmd的终端显示(cmd1确实被回收了,在cmd2内查不到cmd1的pid号),如果将子进程设置为后台运行,就会发现在我们杀死cmd1时,cmd1窗口就会立即关闭(进程与进程的内存空间彼此是隔离的)

obj.terminate():用于杀死子进程

obj.is_alive(): 判断一个子进程是否存活

猜你喜欢

转载自blog.csdn.net/ltfdsy/article/details/82421880
今日推荐