3

我一直在用头撞墙。
我知道如果我在 Powershell 中创建一个数组,然后复制该数组,它会将其复制为引用类型而不是值类型。
所以,经典的例子是:

$c = (0,0,0)
$d = $c
$c[0] = 1
$d
1
0
0

解决方案是$d = $c.clone() 如果数组本身是引用类型的集合,这将不起作用。这是我的问题。我正在尝试通过创建一个进程数组来创建一个数组来跟踪 CPU 使用情况,等待一段时间,然后检查最新值并计算差异。但是,Get-Process 创建一个引用数组。因此,当我执行以下操作时:

$a = ps | sort -desc id | where-object {$_.CPU -gt 20} #Get current values
$b = $a.clone() #Create a copy of those values.
sleep 20 #Wait a few seconds for general CPU usage...

$a = ps | sort -desc id | where-object {$_.CPU -gt 20} #Get latest values.
$a[0]  
$b[0] #returns the same value as A.

Handles  NPM(K)    PM(K)      WS(K) VM(M)   CPU(s)     Id ProcessNam
-------  ------    -----      ----- -----   ------     -- ----------
   3195      57    90336     100136   600    83.71   7244 OUTLOOK

$a并将$b始终返回相同的值。如果我尝试使用 $b[0] = "$a[0].clone()" 之类的东西一次输入一个条目 - PS 抱怨在这种情况下不能使用 Clone。

有什么建议么??

$a = PS |....另外,仅供参考,实际上并不需要第二行,因为它是 PS 列表对象的引用类型,它实际上会被更新并在调用$a时返回最新值。$a我将其包括在内是为了更清楚地说明我在这里要完成的工作。

4

2 回答 2

5

要复制数组,您可以执行以下操作:

$c = (0,0,0)
$d = $c | foreach { $_ }
$c[0] = 1
"c is [$c]"
"d is [$d]"

结果

c is [1 0 0]
d is [0 0 0]

正如基思指出的那样,对于您的特定问题(比较进程的 CPU 使用率),更具体的东西可能会更好。

于 2012-09-18T21:11:02.907 回答
1

从技术上讲$d = $c,它不是任何类型的数组副本(引用或值)。它只是将 $c 所引用的数组的引用存储到 $d 中。我认为您只需要获取一次进程数组,然后调用该Refresh方法即可。您必须首先检查该Exited属性以确保关联的进程仍在运行。当然,如果您对启动的任何新流程感兴趣,这对您没有帮助。在这种情况下,获取不同时间的进程快照,除掉两个数组之间的进程交集之外的所有进程(通过进程 ID),然后计算它们的属性值的差异 - 再次基于进程 ID。让这更容易,您可能希望将每个快照放在一个以进程 ID 为键的哈希表中。

于 2012-09-18T17:47:07.197 回答