Python使用eventlet包超时检测出现了问题?
我使用eventlet包进行代码的超时检测,但是检测的内容不同,怎么结果就不同呢??
text1.py
import eventlet,time #导入该包和time模块eventlet.monkey_patch() #猴子补丁
t = 1 #设置超时时间为1秒
#这行语句下的语句块是超时检测的内容
with eventlet.Timeout(t,False): #第一个参数:超时时间,超过该时间则执行后面的语句
time.sleep(3) #程序挂起3秒
print("OK!") #如果没有超时,则输出提示“OK!”
print("Time Out!") #如果超时则输出提示“Time Out!”
#程序等待1秒后输出:Time Out!
text2.py
import eventlet,socket #导入该包和socket模块s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM) #建立UDP连接
s.sendto("Hello Python".encode(),("33.33.33.33",8888)) #试图向无效IP(33.33.33.33:8888)发送消息“Hello Python”
print("已发送") #发送后输出提示
eventlet.monkey_patch() #猴子补丁
t = 1 #设置超时时间为1秒
with eventlet.Timeout(t,False): #第一个参数:超时时间,超过该时间则执行后面的语句
data,addr = s.recvfrom(1024) #接收消息
if data: #如果接收到了消息则输出提示
print("接收到了消息!")
print(data.decode())
s.close() #关闭套接字
print("没有接收到消息!") #如果超时则输出“没有接收到消息!”
s.close() #关闭套接字
#程序显示“已发送”后就陷入死循环
请问各位大佬,这是怎么回事?在线等,急!
回答:
1.如果仅仅是为了在网络通讯的是进行超时控制
我也比较认同使用timeout控制,比如
python">import sockets = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # 建立UDP连接s
s.settimeout(1) # <------------------ 1秒内无法完成通讯抛超时异常
s.sendto("Hello Python".encode(), ("33.33.33.33", 8888))
try:
data, addr = s.recvfrom(1024) # 接收消息
print(data)
except socket.timeout: # 超时会引发异常
print("没有接收到消息!") # 如果超时则输出“没有接收到消息!”
2. 如果是为了搞清楚text2.py为何无效
2.1. 首先,eventlet是一个协程库
用来实现和管理协程,使得网络通讯具有更高的并发,从这个角度讲,你选择eventlet进行网络超时在控制没毛病
2.2. 那么,eventlet是如何做到这一点呢?
首先通过猴子补丁替修改python原本的底层模块,使之支持切换调度,然后再用eventlet进行管理。
划重点,先通过猴子补丁替修改python原本的底层模块,这是eventlet正常工作的前提。
再来回顾一下text2.py的代码
import eventlet,socket s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM) #socket实例已创建
s.sendto("Hello Python".encode(),("33.33.33.33",8888))
eventlet.monkey_patch() #再用猴子补丁
思考一个问题:
猴子补丁修改某个类,会有已有的实例对象有响应吗?
如果有兴趣的话,我们新开一个帖子聊这个问题,
现在,我们先解决问题: 猴子补丁在前,创建socket在后
修改之后,控制超时成功的例子:
import socketimport eventlet
# 代码第一件事情,使用猴子补丁,其他地方不变
eventlet.monkey_patch()
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # 建立UDP连接
s.sendto(
"Hello Python".encode(), ("33.33.33.33", 8888)
) # 试图向无效IP(33.33.33.33:8888)发送消息“Hello Python”
print("已发送") # 发送后输出提示
t = 1 # 设置超时时间为1秒
with eventlet.Timeout(t, False): # 第一个参数:超时时间,超过该时间则执行后面的语句
data, addr = s.recvfrom(1024) # 接收消息
if data: # 如果接收到了消息则输出提示
print("接收到了消息!")
print(data.decode())
s.close() # 关闭套接字
print("没有接收到消息!") # 如果超时则输出“没有接收到消息!”
s.close() # 关闭套接字
segmentfault首答,如果有帮助,请点赞支持一下
回答:
不用这么麻烦吧,s.setsockopt可以设置socket客户端接受消息的超时时间
以上是 Python使用eventlet包超时检测出现了问题? 的全部内容, 来源链接: utcz.com/a/162103.html