我需要获取有关可执行文件名 strModule 的第三方程序实例的信息并对其进行操作,该程序生成了数百个实例。每个实例都使用不同的命令行参数生成。为了获取有关这些实例的信息并对其进行操作,我结合使用了 WMI 和 Process.GetProcessesByName()。
我有时需要按进程创建时间顺序对实例进行操作,有时需要按命令行的字母顺序对实例进行操作。第一部分很简单,因为默认情况下 WMI 已经按创建时间顺序返回进程,并且我可以轻松地按创建时间对 GetProcessesByName() 返回的进程进行排序。我可以做一些类似的事情:
ManagementObjectSearcher objWMISearcher = new ManagementObjectSearcher(
"SELECT ProcessID, CommandLine FROM Win32_Process WHERE Name = \"" + strModule + ".exe\"");
ManagementObjectCollection aobjWMIs = objWMISearcher.Get();
Process[] aprc = Process.GetProcessesByName(strModule).OrderBy(x => x.StartTime).ToArray();
// I would like to sort aobjWMIs and aprc alphabetically by command line here,
// before entering the foreach loop
int nInstance = -1;
foreach (ManagementObject objWMI in aobjWMIs)
{
nInstance++;
// Code that does stuff on objWMI and aprc[nInstance]
}
我的代码运行良好,并且按照创建时间的顺序对实例进行操作时,可以完成所有应该做的事情。
问题是,我有时需要通过命令行按字母顺序而不是按创建时间顺序对实例进行操作。
我的第一个想法是将“ORDER BY”添加到 WMI SELECT 查询中,但这不起作用,我很失望地在文档中看到 WQL 只是 SQL 的一个非常有限的子集,显然不支持“ORDER BY”。
所以我需要的是某种通过命令行对 aobjWMI 进行排序的方法,在我上面发布的代码中,它说“我想在 foreach 循环之前按命令行按字母顺序排序”。
我的直觉是,有一些简单的方法使用 LINQ 首先对 ManagementObjectCollection aobjWMI 进行排序。然后,我们可以使用 LINQ 将 aprc 每个元素的 .Id 字段与 aobjWMIs 每个元素的 ProcessID 字段进行匹配,以对 aobjWMIs 进行排序,以便 ManagementObjectCollection aobjWMIs 和 Process[] aprc 都具有相同顺序的 strModule 实例。
但是,我不熟练使用 LINQ,不知道如何执行此操作。有人可以帮忙吗?谢谢。
您首先需要将 WMI 结果从对象转换为具体的 C# 类型。例如
var tmpArray = (from mo in aobjWMIs.OfType<ManagementObject>() select new
{
ProcessID = Convert.ToInt32 (mo.Properties["ProcessID" ].Value),
CommandLine = Convert.ToString(mo.Properties["CommandLine"].Value)
}
).ToArray();
因此您现在可以连接两个数组并通过命令行对结果进行排序,例如
var results = (from mo in tmpArray
join p in aprc on mo.ProcessID equals p.Id
orderby mo.CommandLine
select new { mo.ProcessID, mo.CommandLine , p }
).ToArray();