使用多进程,实现多个用户交互
server:
import socket from multiprocessing import Process def talk(conn): conn.send(b'hello') ret=conn.recv(1024) print(ret) if __name__=='__main__': sk=socket.socket() sk.bind(('127.0.0.1',8090)) sk.listen() while 1: conn,addr=sk.accept() p=Process(target=talk,args=(conn,)) p.start() conn.close() sk.close()#利用并发编程,实现多用户交互
client:
import socket sk=socket.socket() sk.connect(('127.0.0.1',8090)) ret=sk.recv(1024) print(ret) info=input('>>>') sk.send(info.encode('utf-8')) sk.close()
结果:
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py b'hello1' b'hello 1' b'hello 2'
一,,守护进程
daemon
早没有demon之前
import time from multiprocessing import Process def func(): print('nn') time.sleep(2) print('vv') if __name__=='__main__': p=Process(target=func) # p.daemon = True p.start() p1 = Process(target=func) p1.start() for i in range(10): print('#'*i)
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py # ## ### #### ##### ###### ####### ######## ######### nn nn vv vv Process finished with exit code 0
在加了守护后
import time from multiprocessing import Process def func(): print('nn') time.sleep(2) print('vv') if __name__=='__main__': p=Process(target=func) p.daemon = True p.start() p1 = Process(target=func) p1.start() for i in range(10): print('#'*i)
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py # ## ### #### ##### ###### ####### ######## ######### nn vv Process finished with exit code 0
守护进程会随着主进程的代码执行结束而结束,正常的时候,子进程没有执行完,主进程要一直等着
需要注意的是,一定要在开启进程之前设置,也就是在start之前
守护进程的作用:
会随着主进程的代码执行结束而结束,不会等待其他子进程
在守护进程中,不能开启子进程
关于进程的两个方法
is_alive()判断进程是否还活着,返回bool值
terninate()终结进程
import time from multiprocessing import Process def func(): print('nn') time.sleep(2) print('vv') if __name__=='__main__': p=Process(target=func) p.start() print('#'*3) print(p.is_alive()) # time.sleep() p.terminate() print(p.is_alive())
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py ### True True
import time from multiprocessing import Process def func(): print('nn') time.sleep(2) print('vv') if __name__=='__main__': p=Process(target=func) p.start() print('#'*3) print(p.is_alive()) time.sleep(1) p.terminate() time.sleep(1) print(p.is_alive())
### True nn False
这里需要注意的是,结束一个进程的时候,不会立刻结束,
再介绍下两个属性
1,pid 查看进程的id
2,name 查看进程的名字
进程的名字可以是可以自己更改的
from multiprocessing import Process def func(): print('hello') if __name__=='__main__': p=Process(target=func) p.start() print(p.pid) print(p.name) p.name='wahah' print(p.name)
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py 12056 Process-1 wahah hello Process finished with exit code 0
Lock
lock.acquire()需要锁 阻塞
lock.release() 释放锁,还钥匙
这里。我们通过一个简陋的模拟抢票的功能,说明
原本有两张票,10个人一起抢,最后只能是有两个人能抢到,
锁的用处就是,每次只能一进程,后面的必须要等到释放锁以后
import json import random,time from multiprocessing import Lock from multiprocessing import Process def search(i): with open('user1')as f: print(i,json.load(f)['count']) def get(i): with open('user1')as f: re=json.load(f)['count'] time.sleep(random.random()) if re >0: with open('user1','w')as f: json.dump({'count':re - 1},f) print('%s有票'%i) else: print('%s没票'%i) def te(i,lock): search(i) lock.acquire() get(i) lock.release() if __name__=='__main__': lock=Lock() for i in range(10): p=Process(target=te,args=(i,lock)) p.start()
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py 0 0 1 0 2 0 3 0 4 0 5 0 6 0 7 0 8 0 9 0 0没票 1没票 2没票 3没票 4没票 5没票 6没票 7没票 8没票 9没票 Process finished with exit code 0
信号量:
Semaphore
信号量的作用就是每次一进一出的原理,
import time from multiprocessing import Semaphore from multiprocessing import Process def sing(i,sem): sem.acquire() print('%s进入'%i) time.sleep(1) print('%s出' %i) sem.release() if __name__=='__main__': sem = Semaphore(2) for i in range(10): Process(target=sing,args=(i,sem)).start()
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py
0进入
1进入
0出
2进入
1出
3进入
2出
4进入
3出
5进入
4出
6进入
5出
7进入
6出
8进入
7出
9进入
8出
9出
Process finished with exit code 0
时间:Event
事件,属于异步阻塞
e=Event()实例化一个对象
e.set()将标志变成非阻塞
e.wait()默认阻塞
e.clear()将标志变成阻塞
e.is_set()是否阻塞
import random,time from multiprocessing import Event,Process def trafic(e): while 1: if e.is_set(): time.sleep(3) print('红灯亮') e.clear() else: time.sleep(3) print('绿灯亮') e.set() def car (i,e): e.wait() print('%s车通过'%i) if __name__=='__main__': e=Event() tra=Process(target=trafic,args=(e,)) tra.start() for i in range(100): if i%6==0: time.sleep(random.randint(1,3)) car_1=Process(target=car,args=(i,e)) car_1.start()
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py
绿灯亮
0车通过
红灯亮
绿灯亮
18车通过
12车通过
6车通过
24车通过
红灯亮
绿灯亮
30车通过
36车通过
42车通过
红灯亮
绿灯亮
48车通过
54车通过
红灯亮
绿灯亮
60车通过
66车通过
72车通过
红灯亮
绿灯亮
78车通过
84车通过
红灯亮
绿灯亮
90车通过
96车通过
进程之间的通信:
队列
from multiprocessing import Process from multiprocessing import Queue import time #这里有一个生产者消费者模型 def a(q):#代表生产者 for i in range(100): q.put('第%s个包子'%i) def b(q):#代表消费者 for i in range(100): time.sleep(2) print('吃掉',q.get()) if __name__=='__main__': q=Queue(10) p=Process(target=a,args=(q,)) p.start() p1 = Process(target=b, args=(q,)) p1.start() p2 = Process(target=b, args=(q,)) p2.start()
C:UsershcAppDataLocalProgramsPythonPython36python3.exe C:/s9/day36/ji.py
吃掉 第0个包子
吃掉 第1个包子
吃掉 第2个包子
吃掉 第3个包子
吃掉 第4个包子
吃掉 第5个包子
吃掉 第6个包子
吃掉 第7个包子
吃掉 第8个包子
吃掉 第9个包子
吃掉 第10个包子
吃掉 第11个包子
吃掉 第12个包子
吃掉 第13个包子
一方生产过快,一方消费慢,为了预防一下子读出太多,所以我们一限制每次拿出的数量,可以增加消费者来来达成平衡