如何在调用process.GetProcessById之前检查进程是否仍在运行
本文关键字:进程 检查 是否 运行 调用 process GetProcessById | 更新日期: 2023-09-27 18:00:18
在.NET中,如果具有此ID的进程未运行,Process.GetProcessById
将引发异常。如何安全地调用此方法,使其不会引发异常?我在想类似的东西
if(Process.IsRunning(id)) return Process.GetProcessById(id);
else return null; //or do something else
但是找不到任何方法来检查ID,除了可能获取所有正在运行的进程并检查ID是否存在于列表中。
public Process GetProcByID(int id)
{
Process[] processlist = Process.GetProcesses();
return processlist.FirstOrDefault(pr => pr.Id == id);
}
我查看了Process.GetProcessById
方法内部。
它使用内部静态类ProcessManager来确保进程运行。ProcessManager获取系统中当前运行的所有进程并检查ID,所以我认为这是最好的方法
因此,您应该考虑异常的开销或Process
数组的开销。
只需使用try-catch块
Process p = null;
try{
p = Process.GetProcessById(id);
}
catch(Exception){
}
return p;
是的,使用try+catch可能会成功。如果进程没有运行,除了抛出异常之外,什么都不会发生。
与使用pinvoke的代码相同,这应该比GetProcesses更快,因为它不需要枚举所有进程。
[DllImport("kernel32.dll", SetLastError = true)]
public static extern IntPtr OpenProcess(ProcessAccessFlags access, bool inheritHandle, int procId);
[DllImport("kernel32.dll", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool CloseHandle(IntPtr hObject);
[DllImport("kernel32.dll", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool GetExitCodeProcess(IntPtr hProcess, out uint lpExitCode);
[Flags]
public enum ProcessAccessFlags : uint
{
All = 0x001F0FFF,
Terminate = 0x00000001,
CreateThread = 0x00000002,
VirtualMemoryOperation = 0x00000008,
VirtualMemoryRead = 0x00000010,
VirtualMemoryWrite = 0x00000020,
DuplicateHandle = 0x00000040,
CreateProcess = 0x000000080,
SetQuota = 0x00000100,
SetInformation = 0x00000200,
QueryInformation = 0x00000400,
QueryLimitedInformation = 0x00001000,
Synchronize = 0x00100000
}
/// <summary>
/// Checks if given process is still alive
/// </summary>
/// <param name="processId">process id</param>
/// <returns>true if process is alive, false if not</returns>
static public bool IsProcessAlive(int processId)
{
IntPtr h = OpenProcess(ProcessAccessFlags.QueryInformation, true, processId);
if (h == IntPtr.Zero)
return false;
uint code = 0;
bool b = GetExitCodeProcess(h, out code);
CloseHandle(h);
if (b)
b = (code == 259) /* STILL_ACTIVE */;
return b;
}