Open ls0f opened 8 years ago
很多时候都会有这样的需求,当一个函数多少时间内没执行完的时候,就pass执行下一个任务,避免盲等,这在boss-worker型的系统中尤为明显。那么我们怎么来设计这个计时器呢?
如果我们自己来实现,最简单的做法是开另外一个线程来计时。当到时间的时候发送一个信号给另外一个线程。实际Linux内核已经实现了这个功能。
使用alarm可以设置一个定时器,在将来某个时间内计时器会超时,产生SIGALRM信号。如果程序没有处理这个信号,默认是终止程序。每个进程只有一个alarm时钟,多次调用会覆盖上一次设置的值,以最新的指为准。alarm(0)则是取消闹钟。
alarm
SIGALRM
alarm(0)
有了alarm,我们便可以很方便的在程序中设置TimeOut。下面是一个Python的简单实现:
class TimeOutError(Exception): pass class TimeOut(object): def __init__(self, seconds=1, error_message='TimeOut'): self.seconds = seconds self.error_message = error_message def handle_timeout(self, signum, frame): raise TimeOutError(self.error_message) def __enter__(self): signal.signal(signal.SIGALRM, self.handle_timeout) signal.alarm(self.seconds) def __exit__(self, type, value, traceback): signal.alarm(0) with TimeOut(2): requests.get("http://httpbin.org/delay/3")
requests.get 将会触发自定义的TimtOutError。
TimtOutError
很多时候都会有这样的需求,当一个函数多少时间内没执行完的时候,就pass执行下一个任务,避免盲等,这在boss-worker型的系统中尤为明显。那么我们怎么来设计这个计时器呢?
如果我们自己来实现,最简单的做法是开另外一个线程来计时。当到时间的时候发送一个信号给另外一个线程。实际Linux内核已经实现了这个功能。
使用
alarm
可以设置一个定时器,在将来某个时间内计时器会超时,产生SIGALRM
信号。如果程序没有处理这个信号,默认是终止程序。每个进程只有一个alarm时钟,多次调用会覆盖上一次设置的值,以最新的指为准。alarm(0)
则是取消闹钟。有了
alarm
,我们便可以很方便的在程序中设置TimeOut。下面是一个Python的简单实现:requests.get 将会触发自定义的
TimtOutError
。