发布于2020-03-12 16:00 阅读(1621) 评论(0) 点赞(24) 收藏(0)
multiprocessing
import multiprocessing
def test(n):
name = multiprocessing.current_process().name
print(name,"starting")
print("is",n)
return
if __name__ == '__main__':
num_list =[]
for i in range(10):
p = multiprocessing.Process(target=test,args=(i,))
num_list.append(p)
p.start()
#join是阻塞主进程等待子进程返回
p.join()
print(multiprocessing.cpu_count())
print("End")
print(num_list)
上面的例子中使用multiprocessing中的Process来创建进程,target为执行的方法,传入函数,args为方法需要传入的参数,此外还可设置group,name等,group一般不会用到,join为阻塞主进程,cpu_count()来获取copu的核数。name来命名子进程。进程有创建,就绪,运行,阻塞与结束共5个状态,start()方法为就绪并不是运行,告知CPU让系统来进行调度安排。
from multiprocessing import Pool
def func(n):
return n**2
if __name__ == '__main__':
pool = Pool(processes=4)
#异步非阻塞
result = pool.apply_async(func,[10])
print(result.get(timeout=1))
print(pool.map(func,range(10)))
processes意思为开4个进程,一个cpu开一个进程,apply_async为异步启动,如一个任务有4个步骤,使用异步的话就不需要按顺序执行,执行1的同时可以执行2,不需要等待。进程池里还有close()和join()、map()等方法,close()为禁止往进程池添加任务,join()与普通的多进程相仿,map(func,iterate)与python中的map一样迭代队列执行func。
from multiprocessing import Process,Queue
def set_data(queue):
for i in range(10):
queue.put("hello"+str(i))
def get_data(queue):
for i in range(10):
print(queue.get())
if __name__ == '__main__':
q = Queue()
p1 = Process(target=set_data,args=(q,))
p2 = Process(target=get_data,args=(q,))
p1.start()
p2.start()
p1.join()
p2.join()
print("空...空了吗?",q.empty())
一个进程往队列添加数据,一个进程取走数据,使用这种方法在爬虫之中,可以一个进程存储未爬取的url,一个进程获取,来提高爬取数据的速度。
from multiprocessing import Process,Lock,Semaphore
def test_lock(lock,n):
lock.acquire()#获得锁
print("this is ",n)
lock.release()#最后解锁释放
if __name__ == '__main__':
lock = Lock()
# s = Semaphore(3)
for i in range(10):
Process(target=test_lock,args=(lock,i)).start()
在多进程中,可能在同一时间对一个变量进行访问修改,这时候需要加把锁来锁住,防止一边在修改并且提交了修改后的数据,另一边访问到未修改前的数据并对其修改。加锁可以保证数据的稳定性与安全性,multiprocessing中有2种方式加锁,一种是Lock,一种是Semaphore,后者可以设置同时多少个进程进行访问。
from multiprocessing import Process,Event
def wait(event):
print("wait~~~")
event.wait()
print("event.is_set",event.is_set())
def wait_timeout(event,t):
print("timeout!!!")
print()
print("event.is_set", event.is_set())
event.set()#设置为真
if __name__ == '__main__':
event = Event()
print(event.is_set())
t1 = Process(target=wait,args=(event,))
t1.start()
t2 = Process(target=wait_timeout,args=(event,2))
t2.start()
print("set event")
在multiprocessing中可以使用Event来进行进程间的通讯,通过is_set()方法来获取当前状态来进行下一步的操作,wait()方法为阻塞等待,如果未接到可执行信号时将一直阻塞。timeout()顾名思义则是超时设置,在超过多少时间后进行信号的设置,然后进行下一步的操作。可以把wait_timeout中的event.set()注释掉来查看具体的效果。
from multiprocessing import Process,Pipe
def p1(pipe):
pipe.send('pipe1')
print("pipe1 received: %s"%pipe.recv())
pipe.send("who are you")
print("pipe1 received: %s"%pipe.recv())
def p2(pipe):
pipe.send('pipe2')
print("pipe2 received: %s"%pipe.recv())
pipe.send("this is a bad problem")
print("pipe2 received: %s"%pipe.recv())
if __name__ == '__main__':
pipe = Pipe()
#第一个管道对象传入第一个进程
process1 = Process(target=p1,args=(pipe[0],))
# 第二个管道对象传入第二个进程
process2 = Process(target=p2,args=(pipe[1],))
process1.start()
process2.start()
process1.join()
process2.join()
管道可以看做是两个进程之间进行消息的互通,可以设置单向管道,默认为双向的管道,管道的端口智能由一个进程来使用,否则出现错误。用send来发送消息,recv来接收消息。
from multiprocessing import Process,Value,Array
def func(n,a):
n.value = 200
for i in range(len(a)):
a[i] = -a[i]
if __name__ == '__main__':
num = Value('d',0.0)
print(num.value)
arr = Array('i',range(10))
print(arr[:])
p = Process(target=func,args=(num,arr))
p.start()
p.join()
print(num.value)
print(arr[:])
在multiprocessing中使用Value和Array来进行变量的共享,value是创建变量大小的共享内存,Array是创建数组大小的共享内存,第一个参数为创建的类型。进程之中的变量为独立的,而num和arr为主进程的变量,通过Value和Array,可以在子进程中进行修改。
原文链接:https://blog.csdn.net/qq_29755301/article/details/104736662
作者:恋爱后女盆友的变化
链接:https://www.pythonheidong.com/blog/article/254390/5086d2696e9f45c171a8/
来源:python黑洞网
任何形式的转载都请注明出处,如有侵权 一经发现 必将追究其法律责任
昵称:
评论内容:(最多支持255个字符)
---无人问津也好,技不如人也罢,你都要试着安静下来,去做自己该做的事,而不是让内心的烦躁、焦虑,坏掉你本来就不多的热情和定力
Copyright © 2018-2021 python黑洞网 All Rights Reserved 版权所有,并保留所有权利。 京ICP备18063182号-1
投诉与举报,广告合作请联系vgs_info@163.com或QQ3083709327
免责声明:网站文章均由用户上传,仅供读者学习交流使用,禁止用做商业用途。若文章涉及色情,反动,侵权等违法信息,请向我们举报,一经核实我们会立即删除!