Python装饰器限制函数运行时间超时则退出执行
实际项目中会涉及到需要对有些函数的响应时间做一些限制,如果超时就退出函数的执行,停止等待。
可以利用python中的装饰器实现对函数执行时间的控制。
python装饰器简单来说可以在不改变某个函数内部实现和原来调用方式的前提下对该函数增加一些附件的功能,提供了对该函数功能的扩展。
方法一.使用signal
#coding=utf-8
importsignal
importtime
defset_timeout(num,callback):
defwrap(func):
defhandle(signum,frame):#收到信号SIGALRM后的回调函数,第一个参数是信号的数字,第二个参数是theinterruptedstackframe.
raiseRuntimeError
defto_do(*args,**kwargs):
try:
signal.signal(signal.SIGALRM,handle)#设置信号和回调函数
signal.alarm(num)#设置num秒的闹钟
print('startalarmsignal.')
r=func(*args,**kwargs)
print('closealarmsignal.')
signal.alarm(0)#关闭闹钟
returnr
exceptRuntimeErrorase:
callback()
returnto_do
returnwrap
defafter_timeout():#超时后的处理函数
print("Timeout!")
@set_timeout(2,after_timeout)#限时2秒超时
defconnect():#要执行的函数
time.sleep(3)#函数执行时间,写大于2的值,可测试超时
print('Finishedwithouttimeout.')
if__name__=='__main__':
connect()
方法一中使用的signal有所限制,需要在linux系统上,并且需要在主线程中使用。方法二使用线程计时,不受此限制。
方法二.使用Thread
#-*-coding:utf-8-*-
fromthreadingimportThread
importtime
classTimeoutException(Exception):
pass
ThreadStop=Thread._Thread__stop
deftimelimited(timeout):
defdecorator(function):
defdecorator2(*args,**kwargs):
classTimeLimited(Thread):
def__init__(self,_error=None,):
Thread.__init__(self)
self._error=_error
defrun(self):
try:
self.result=function(*args,**kwargs)
exceptException,e:
self._error=str(e)
def_stop(self):
ifself.isAlive():
ThreadStop(self)
t=TimeLimited()
t.start()
t.join(timeout)
ifisinstance(t._error,TimeoutException):
t._stop()
raiseTimeoutException('timeoutfor%s'%(repr(function)))
ift.isAlive():
t._stop()
raiseTimeoutException('timeoutfor%s'%(repr(function)))
ift._errorisNone:
returnt.result
returndecorator2
returndecorator
@timelimited(2)#设置运行超时时间2S
deffn_1(secs):
time.sleep(secs)
return'Finishedwithouttimeout'
defdo_something_after_timeout():
print('Timeout!')
if__name__=="__main__":
try:
print(fn_1(3))#设置函数执行3S
exceptTimeoutExceptionase:
print(str(e))
do_something_after_timeout()
总结
以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,谢谢大家对毛票票的支持。如果你想了解更多相关内容请查看下面相关链接