我正在使用以下代码以编程方式启动Internet Explorer:
ProcessStartInfo startInfo = new ProcessStartInfo("iexplore.exe"); startInfo.WindowStyle = ProcessWindowStyle.Hidden; startInfo.Arguments = "http://www.google.com"; Process ieProcess = Process.Start(startInfo);
这将生成2个在Windows任务管理器中可见的进程。然后,我尝试使用以下方法终止该进程:
ieProcess.Kill();
这导致任务管理器中的一个进程被关闭,而另一个保持不变。我尝试检查任何具有子进程的属性,但均未找到。我如何也可以杀死其他进程?更一般而言,如何杀死与以Process.Start开始的进程相关的所有进程?
这对我来说非常有效:
/// <summary> /// Kill a process, and all of its children, grandchildren, etc. /// </summary> /// <param name="pid">Process ID.</param> private static void KillProcessAndChildren(int pid) { // Cannot close 'system idle process'. if (pid == 0) { return; } ManagementObjectSearcher searcher = new ManagementObjectSearcher ("Select * From Win32_Process Where ParentProcessID=" + pid); ManagementObjectCollection moc = searcher.Get(); foreach (ManagementObject mo in moc) { KillProcessAndChildren(Convert.ToInt32(mo["ProcessID"])); } try { Process proc = Process.GetProcessById(pid); proc.Kill(); } catch (ArgumentException) { // Process already exited. } }
在Visual Studio 2015 Update 2上进行了测试Win7 x64。现在仍然像3年前一样运作良好。
Visual Studio 2015 Update 2
Win7 x64
添加了对系统空闲过程的检查 if (pid == 0)
if (pid == 0)
需要添加对System.Management命名空间的引用,请参见下面的@MinimalTech的注释。如果您安装了ReSharper,它将自动为您执行此操作。
System.Management
最常见的用例是杀死我们自己的C#进程已启动的所有子进程。
在这种情况下,更好的解决方案是在C#中使用Win32调用,使所有生成的进程成为子进程。这意味着在退出父进程时,Windows将自动关闭所有子进程,从而无需使用上面的代码。如果您要我发布代码,请告诉我。