一个程序运行起来后,代码+用到的资源 称之为进程,它是 *** 作系统分配资源的基本单元。
Pass:进程是资源分配的最小单位,线程是cpu调度的最小单位
2、进程中的状态工作中,任务数往往大于CPU核数,也就是说有部分任务正在执行,也有另一部分任务正在等待CPU进行执行,也就出现了不同的状态。
五种进程状态:新建、就绪、堵塞、运行、死亡
- 就绪态:运行的条件都已经满足,等待CPU执行
- 执行态:正在执行的进程
- 等待态:满足运行条件之后,等待CPU执行
import os # 多种 *** 作系统接口模块
from multiprocessing import Process #在multiprocessing模块中导入process类
def f1():
print(f'f1子进程的id是{os.getpid()},父进程id为{os.getppid()}')
def f2():
print(f'f2子进程的id是{os.getpid()},父进程id为{os.getppid()}')
if __name__ == '__main__':
# 创建子进程
p1 = Process(target=f1)
p2 = Process(target=f2)
# 启动进程
p1.start()
p2.start()
# 修改进程名
p1.name = 'our'
print('p1的子进程名是',p1.name)
print(f'主进程的id是{os.getpid()},父进程id为{os.getppid()}')
# 结果:
# p1的子进程名是 our
# 主进程的id是18532,父进程id为7904
# f1子进程的id是1632,父进程id为18532
# f2子进程的id是26292,父进程id为18532
2、常用的方法 is_alive()和join()
start()启动
is_alive()判断进程子进程是否还活着,如果存活则返回True,否则为False;
join() 阻塞
terminate()不管任务是否完成,立即终止进程
例子1:
from multiprocessing import Process
def study(name):
print(f'{name}学习很认真')
def smile(name):
print(f'{name}能笑到最后呢')
if __name__ =='__main__':
p1 = Process(target=study,args=('任嘉伦',))
p2 = Process(target=smile,args=('任国超',))
p1.start()
p2.start()
print('p1的状态是',p1.is_alive())
print('p2的状态是',p2.is_alive())
# 结果:
# p1的状态是 True
# p2的状态是 True
# 任嘉伦学习很认真
# 任国超能笑到最后呢
例子2:
# 创建的进程带参数
from multiprocessing import Process
def study(name):
print(f'{name}学习很认真')
def smile(name):
print(f'{name}能笑到最后呢')
if __name__ =='__main__':
p1 = Process(target=study,args=('任嘉伦',))
p2 = Process(target=smile,args=('任国超',))
p1.start()
p1.join()#添加阻塞主进程
p2.start()
p2.join()#添加阻塞主进程
print('p1的状态是',p1.is_alive())
print('p2的状态是',p2.is_alive())
# 结果:
# 任嘉伦学习很认真
# 任国超能笑到最后呢
# p1的状态是 False
# p2的状态是 False
3、子进程之间资源不共享
from multiprocessing import Process
import time
li = [] # 全局变量,空列表
def f1():
for i in range(3):
li.append(i)
time.sleep(1) # 停1s
print('这是f1中的:',li)
def f2():
print('这是f2中的:',li)
if __name__=='__main__':
p1 = Process(target=f1)
p2 = Process(target=f2)
p1.start()
p1.join()
p2.start()
p2.join()
# 结果:
# 这是f1中的: [0]
# 这是f1中的: [0, 1]
# 这是f1中的: [0, 1, 2]
# 这是f2中的: []
三、进程的通信–队列Queue
1、定义
使用队列Queue实现多进程之间的数据传递
原则:先进先出
- 入队:将一个数据放到队列的尾部;
- 出队:从队列的头部取出一个元素
- 初始化Queue()对象 如q = Queue()
- q.empty() 判断队列是否为空
- q.get() 到队列中去取值
- q.put() 把数据放入队列中
- q.full() 判断这个队列是否是满的
- q.qsize() 返回队列的大小
例子1:
from queue import Queue
q = Queue(3) # 最多接收3个数据
# 放数据到队列中
q.put('任嘉伦')
q.put('任国超')
q.put('Allen')
print(q.full()) # True
# 到队列中取值
print(q.get())#任嘉伦
print(q.get())#任国超
print(q.get())#Allen
例子2:
from queue import Queue
q = Queue(3) # 最多接收3个数据
# 放数据到队列中
q.put('任嘉伦')
q.put('任国超')
print(q.full()) # FALSE,只放了2个数据放到队列
# 到队列中取值
print(q.get())#任嘉伦
print(q.get())#任国超
print(q.get())
3、实现通信
进程1先将数据放入队列中,进程2再去队列中取,队列就相当于一座桥梁;
使用到的方法:
- 初始化Queue()对象 如q = Queue()
- q.empty() 判断队列是否为空
- q.get() 到队列中去取值
- q.put() 把数据放入队列中
from multiprocessing import Process,Queue
import time
import random
lst = [1,2,3,4] # 消息数据
# 往队列中放数据
def write(q):
for i in lst:
print(f'将{i}放入队列中')
q.put(i)
time.sleep(random.random()) # random.random() 表示0-1之间的实数
# 从列队中读(取)数据
def read(q):
while True:
if not q.empty(): # 判断队列不为空时
info = q.get() # 取值
print(f'从队列中获取的是{info}')
else:
break
if __name__=="__main__":
# 实例化一个队列
q = Queue()
# 创建子进程
p1 = Process(target=write,args=(q,))
p2 = Process(target=read,args=(q,))
# 启动
p1.start()
p1.join()
p2.start()
p2.join()
# 结果:
# 将1放入队列中
# 将2放入队列中
# 将3放入队列中
# 将4放入队列中
# 从队列中获取的是1
# 从队列中获取的是2
# 从队列中获取的是3
# 从队列中获取的是4
四、进程池
1、定义
主程序接受的外部任务通过调度算法分到池子内的进程。
2、同步接完任务后,执行完了,在原地等待,不建议使用
例子:
import time
from multiprocessing import Pool # 导入进程池
def learn(n):
print('好好学习,和任嘉伦一样优秀')
time.sleep(2)
return n**2
if __name__=="__main__":
# 定义一个进程池
p = Pool(3) # 最大进程数3
lst = []
for i in range(6): # i值的范围是0-5
# 同步方式调用任务
res = p.apply(learn,args=(i,)) # args 给learn传实参
lst.append(res) # 把返回结果添加到列表中
print(lst)
3、异步
接完任务后,执行完了,执行其他的任务,效率高
用到的方法:
- p = Pool()
- p.apply_async()异步非阻塞调用任务
- p.close() 关闭进程池
- terminate 终止
- p.join()阻塞
例子:
import time
from multiprocessing import Pool # 导入进程池
def learn(n):
print('好好学习,和任嘉伦一样优秀')
time.sleep(5)
return n*2
if __name__=="__main__":
# 定义一个进程池
p = Pool(2) # 最大进程数2
list = []
for i in range(6): # i值的范围是0-5
# 异步方式调用任务
res = p.apply_async(learn,args=(i,)) # args 给learn传实参
list.append(res) # 把返回结果添加到列表中
p.close() # 关闭进程池,关闭后p不再接收新的任务
p.join() # 等待进程池p中所有子进程执行完成,必须放在close()或terminate()之后
for j in list:
print(j.get()) # 需要用get方法来获取apply_async返回的结果
# 结果:
# 好好学习,和任嘉伦一样优秀
# 好好学习,和任嘉伦一样优秀
# (中间停留5s)
# 好好学习,和任嘉伦一样优秀
# 好好学习,和任嘉伦一样优秀
# (中间停留5s)
# 好好学习,和任嘉伦一样优秀
# 好好学习,和任嘉伦一样优秀
# 0
# 2
# 4
# 6
# 8
# 10
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)