我正在阅读有关信号的信息并试图实施library(stringr)
unlist(strsplit(str_extract_all(string,'(?<=\\=)([^_]+)')[[1]],'--'))
[1] "621729" "twenty" "One" "Forty"
根据我的理解,如果用户在程序运行时按下CTRC + C,将发送一个信号来杀死一个程序。我可以将程序指定为参数吗?
我尝试测试用法:
signal.CTRL_C_EVENT
然而,似乎我需要一个pid号和&#39; python.exe&#39;不起作用。我查看了流程,我似乎无法找到一个PID号码。我确实在服务下看到了一个PID列,但是有很多服务 - 我找不到python。
那么如何找到PID号? 另外,signal_CTRL_C_EVENT总是必须在os.kill中使用吗? 它可以用于其他目的吗?
谢谢。
答案 0 :(得分:1)
你可以通过os.getpid()
获得pidos.kill(os.getpid(), signal.CTRL_C_EVENT)
答案 1 :(得分:1)
Windows没有实现Unix信号,因此Python伪造os.kill
。不幸的是,它的实施令人困惑。 应分为os.kill
和os.killpg
,但我们仍然坚持使用混合两者的实现。要发送Ctrl + C或Ctrl + Break,您需要使用os.kill
,就像它真的是os.killpg
一样。
当signal
参数为CTRL_C_EVENT
(0)或CTRL_BREAK_EVENT
(1)时,os.kill
会调用WinAPI GenerateConsoleCtrlEvent
。这指示控制台(即托管当前进程的控制台窗口的conhost.exe实例)将事件发送到给定进程组 ID(PGID)。组ID 0是特殊的,用于将事件广播到连接到控制台的所有进程。除此以外
进程组ID是进程组中的潜在进程的ID。每个进程都被创建为新组的领导者或继承其父组的组。可以通过CreateProcess
创建标记CREATE_NEW_PROCESS_GROUP
创建新组。
如果调用GenerateConsoleCtrlEvent
失败(例如当前进程未附加到控制台)或signal
参数不是上述控制事件之一,则{{1}而是尝试使用终止访问打开给定进程ID(PID)的句柄并调用WinAPI os.kill
。这个函数就像在Unix中发送TerminateProcess
信号,但是带有变量退出代码。请注意混淆,因为它在单个流程(即SIGKILL
)上运行,而不是流程组(即kill
)。
Windows不提供获取进程的组ID的功能,因此获取有效PGID的唯一方法通常是自己创建进程。您可以通过killpg
参数将CREATE_NEW_PROCESS_GROUP
标记传递给subprocess.Popen
。然后,您可以将Ctrl + Break发送到子进程及其位于同一组中的所有子进程,但前提是它是一个与当前进程连接到同一控制台的控制台进程,即如果您也是也可以使用以下任何标志:creationflags
,CREATE_NEW_CONSOLE
或CREATE_NO_WINDOW
。此外,在此过程中禁用Ctrl + C,除非子项通过WinAPI DETACHED_PROCESS
手动启用它。
当您确定当前流程是作为群组的潜在客户启动时,仅使用SetConsoleCtrlHandler
。否则,行为是未定义的,实际上它的工作方式就像发送到进程组ID 0。