PowerShell数组追加元素失效,进程统计无法写入CSV
问题:PowerShell脚本无法累加进程统计数据并写入CSV
编写的PowerShell脚本用于定期获取指定进程的CPU和内存统计并写入CSV,但执行后CSV始终无数据——全局变量$processStats为空,不过函数Get-ProcessStats内部能正常打印该变量的元素和统计对象。
问题原因
核心是PowerShell的变量作用域规则:默认情况下,函数内的变量属于局部作用域。当你在函数中执行$processStats += $statsObject时,PowerShell会创建一个同名的局部变量,而非修改全局的$processStats。所以函数内看到的是局部变量的内容,而全局的数组始终是空的,最终导出CSV自然没有数据。
解决方法
方法1:显式引用全局变量
在函数中修改$processStats时,加上$global:前缀,明确操作全局变量:
function Get-ProcessStats { param ( [string]$processName ) $process = Get-Process -Name $processName -ErrorAction SilentlyContinue if ($process -ne $null) { $cpuUsage = $process.CPU $memoryUsage = $process.WorkingSet64 Write-Output "$processName - CPU Usage: $cpuUsage%, Memory Usage: $memoryUsage bytes" # Create an object with process stats $statsObject = [PSCustomObject]@{ ProcessName = $processName CPUUsage = $cpuUsage MemoryUsage = $memoryUsage } Write-Output "Stats: $statsObject" # 显式引用全局变量 $global:processStats += $statsObject Write-Output "ProcessStats:" $global:processStats | Format-Table $global:processStats.Count } else { Write-Output "$processName not found." } }
方法2:通过函数返回值收集数据(推荐)
尽量避免使用全局变量,改为让函数返回统计对象,在主循环中收集数据,更符合PowerShell的编程习惯:
# Specify the process names $process1Name = "abcd" $csvFilePath = "C:\Users\johndoe\Stats.csv" # Create an array to store process stats $processStats = @() # Loop to monitor processes every second $exportIntervalInSeconds = 60 # Set the desired export interval $iterationCount = 0 # Function to get CPU and Memory usage of a process function Get-ProcessStats { param ( [string]$processName ) $process = Get-Process -Name $processName -ErrorAction SilentlyContinue if ($process -ne $null) { $cpuUsage = $process.CPU $memoryUsage = $process.WorkingSet64 Write-Output "$processName - CPU Usage: $cpuUsage%, Memory Usage: $memoryUsage bytes" # 返回统计对象 return [PSCustomObject]@{ ProcessName = $processName CPUUsage = $cpuUsage MemoryUsage = $memoryUsage } } else { Write-Output "$processName not found." return $null } } # Loop to monitor processes every second while ($true) { $stats = Get-ProcessStats -processName $process1Name if ($stats -ne $null) { $processStats += $stats } Start-Sleep -Seconds 1 $iterationCount++ if ($iterationCount -ge $exportIntervalInSeconds) { # Export the process stats to CSV Write-Output "Reached export interval, exporting data..." $processStats | Export-Csv -Force -Path $csvFilePath -NoTypeInformation # Reset iteration count and stats array $iterationCount = 0 $processStats = @() } }
验证说明
修改后运行脚本,每到导出间隔时,$processStats会包含这段时间内收集的所有统计对象,导出的CSV文件将正常写入数据。
内容的提问来源于stack exchange,提问作者Sameer Joshi
相关产品推荐
相关产品推荐

