PowerShell系统信息脚本CSV输出格式问题:如何将列输出转换为行输出
PowerShell系统信息脚本CSV输出格式问题:如何将列输出转换为行输出
哈哈,太懂这种“明明肯定有简单办法但就是绕不出来”的感觉了!别慌,你现在的问题出在把哈希表转成对象的方式不对——你循环了哈希表的键,生成了每行一个属性的条目,自然就变成了“列式”输出,而咱们要的是把整台电脑的信息作为单独一行,每个属性对应CSV的一列。
咱们直接来改代码,先理清楚核心问题:
你现在写的ForEach-Object循环是把每个键(比如Timestamp、Hostname)拆成了单独的对象行,这就是为什么输出是列。正确的做法是直接把你的有序哈希表转换成一个PSCustomObject,这样它本身就是一行数据,每个哈希表的键就是CSV的列名,值就是对应列的内容。
还有几个小优化点顺便给你提一下:
- 不用两次调用
Get-WmiObject Win32_OperatingSystem,调用一次存成变量就行,省点资源 - IP地址的获取可以更简洁,不用先转成字符串再匹配,直接过滤
Get-NetIPAddress的结果
下面是修正后的完整代码:
# 注意这里改成你的共享路径,比如"\\domain-share\survey\computers.csv" $loglocation = "\\your-shared-drive\path\to\computers.csv" $timestamp = Get-Date -UFormat "%Y-%m-%d %H:%M" # 优化:只调用一次WMI获取系统信息 $osInfo = Get-WmiObject Win32_OperatingSystem # 优化:直接过滤Get-NetIPAddress的结果,只取10.15开头的IPv4地址 $ipaddress = (Get-NetIPAddress -AddressFamily IPv4 | Where-Object {$_.IPAddress -like "10.15.*"}).IPAddress -join ", " # 有序哈希表不变,这部分没问题 $computerinfohastable = [ordered]@{ Timestamp = $timestamp Hostname = hostname OSName = $osInfo.Caption OSVer = $osInfo.Version IPAddress = $ipaddress } # 核心修正:直接把哈希表转成PSCustomObject,这就是一行数据! $computerinfo = [PSCustomObject]$computerinfohastable # 输出到CSV,-Append是追加,-NoTypeInformation去掉默认的类型信息行 $computerinfo | Export-Csv -Path $loglocation -Append -NoTypeInformation
来给你拆解下关键改动:
- 去掉了多余的循环:你之前的
ForEach-Object把每个属性拆成了单独行,现在直接转哈希表为对象,得到的就是包含所有属性的单行数据 - 优化了WMI调用:一次调用存到变量里,重复使用,效率更高
- IP地址获取更高效:直接用
Where-Object过滤IP,不用字符串替换,更可靠 - CSV输出用-Append:每次运行都会在CSV里新增一行,完美符合你“每次启动加一行到共享CSV”的需求
测试一下的话,第一次运行会创建CSV文件,之后每次启动都会追加一行新的电脑信息,格式就是Timestamp、Hostname、OSName这些作为列,每台电脑的信息占一行,完全是你想要的效果!
备注:内容来源于stack exchange,提问作者SKaye




