在做一些WSGI服务器时,我注意到在循环中对time.sleep()的一些测试调用仅在第一次迭代时才进行。这是一个复制品:
import os
import signal
import time
def run_loop():
i = 0
while True:
print('PID: {}, i = {}'.format(os.getpid(), i))
time.sleep(5) # Only works the first time
i += 1
pid = os.fork() . # May or may not be related?
if pid == 0:
print('PID: {}, CHILD'.format(os.getpid(), i))
os._exit(0)
if __name__ == '__main__':
# If I uncomment this line it works fine.
# If I leave it as is, the time.sleep in run_loop() only waits once.
signal.signal(signal.SIGCHLD, lambda a, b: os.wait())
run_loop()
我知道time.sleep()文档中的以下部分。
实际暂停时间可能小于请求的时间,因为任何捕获的信号将在执行该信号的捕获程序后终止sleep()。
这是因为SIGCHLD
信号在time.sleep()
运行时一直触发吗?什么会导致信号取消每次调用time.sleep()一致?
答案 0 :(得分:2)
来自linux睡眠文档
sleep()导致调用线程休眠,直到数量为止 以秒为单位指定的实时秒数已经过去或直到信号为止 到达时不被忽视。
有一个linux c函数,允许你在被称为' nanosleep'的信号打断后继续睡觉。它要么睡眠一定量的纳秒,要么睡觉直到信号到达并返回剩余的纳秒数但python不会在任何模块中暴露它
您可以自己模拟纳米睡眠所需的相同行为,例如:
import datetime
import time
def busy_sleep(seconds):
start_time = datetime.datetime.now()
seconds_slept = 0
while seconds_slept < seconds:
time.sleep(seconds - seconds_slept)
seconds_slept = (datetime.datetime.now() - start_time).total_seconds()