需要理解Python信号和模块
我正在学习Python,想用它来替代一些C语言的代码。但是我在模块之间共享数据时遇到了问题,可能是我对这个过程的理解不够。我的信号模块简单来说是这样的:
import sys, signal
sigterm_caught = False
def SignalHandler(signum, stackframe):
if signum == signal.SIGTERM:
sigterm_caught = True
sys.stdout.write("SIGTERM caught\n")
def SignalSetup():
signal.signal(signal.SIGTERM, SignalHandler)
而我的主代码有一个像这样的循环:
signals.SignalSetup()
while signals.sigterm_caught == False:
sys.stdout.write("sigterm_caught=%s\n" % str(signals.sigterm_caught))
time.sleep(5)
我运行这个代码,然后结束这个进程。在signals.py里面,它接收到信号,把sigterm_caught设置为True,但主进程中的循环却没有看到sigterm_caught的值发生变化。
所以,(a) 我这样做完全不符合Python的方式吗? (b) 我在引用模块中的变量时做错了什么吗? (c) 我应该以不同的方式处理信号,比如抛出一个异常吗?
补充:处理信号时,抛出异常更好,还是我以前在C语言中的做法仍然有效呢?
2 个回答
3
如果你要对一个全局变量进行写入操作,记得使用 global 关键字:
sigterm_caught = False
def SignalHandler(signum, stackframe):
global sigterm_caught
if signum == signal.SIGTERM:
sigterm_caught = True
sys.stdout.write("SIGTERM caught\n")
8
你需要在处理函数里加一个 global
语句:
def SignalHandler(signum, stackframe):
global sigterm_caught
if signum == signal.SIGTERM:
sigterm_caught = True
sys.stdout.write("SIGTERM caught\n")
在Python中,默认情况下,如果一个函数给某个名字(比如 sigterm_caught
)赋值,编译器就会认为这个名字是这个函数的局部变量。也就是说,这个名字只在这个函数内部有效。加上 global
语句的作用就是告诉编译器,这个名字是全局的,也就是在整个模块中都能用。