Powershell 哈希表未按预期写入文件 - 仅接收“System.Collections”行

问题描述 投票:0回答:7

有人可以解释一下为什么我的第一个示例不起作用,为什么添加 ForEach-Object 可以解决问题?预先感谢!


我将命令的返回解析为哈希表(帖子末尾的示例),并希望将信息记录到文件中作为处理的一部分。我知道

$ht.GetEnumerator() | Sort-Object Name
会将完整的哈希值返回到屏幕,并进行排序。但是,一旦我尝试将内容发送到文件,它就会崩溃。

$ht | Add-Content log.txt

仅记录单行

System.Collections.Hashtable
。所以,我也尝试过

$ht.GetEnumerator() | Sort-Object Name | Add-Content log.txt 

最终会出现一排

System.Collections.DictionaryEntry
System.Collections.DictionaryEntry
System.Collections.DictionaryEntry

然后我尝试循环并单独处理每个

foreach ($key in $ht.keys) {
Add-Content log.txt "$key : $ht.$key" }

最终得到

Server address : System.Collections.Hashtable.Server address
Client address : System.Collections.Hashtable.Client address
User name : System.Collections.Hashtable.User name

解决了

$ht.GetEnumerator() | Sort-Object Name |
ForEach-Object {"{0} : {1}" -f $_.Name,$_.Value} |
Add-Content log.txt 

作为参考,哈希表示例:

$ht = @{
    "Server address" = "server.net";
    "Client address" = "10.20.121.153";
    "User name" = "myuser"
}
powershell hashtable
7个回答
15
投票

回答为什么部分,你显然有一个解决方案:)

在你的第一个例子中

$ht | Add-Content log.txt

PowerShell 获取

$ht
并尝试以某种方式将其转换为字符串,以便可以通过
Add-Content
进行存储。由于没有为哈希表定义转换,因此转换仅返回类型名称。与示例相同
new-Object Random|Add-Content d:\log.txt
。同样,只写类型名称。

下一个

$ht.GetEnumerator() | Sort-Object Name | Add-Content log.txt 

类似。

GetEnumerator
返回用于迭代的对象;返回类型为
System.Collections.DictionaryEntry
的对象。同样,没有转换为字符串,因此返回类型名称。

我个人认为PowerShell应该足够聪明并且可以在这里提供帮助。问题是“如何?”。设计人员可能不想对输出进行硬编码。可能是

"{key}: {value}"
"{key} = {value}"
,或
"{key}/{value}"
,或 ... 格式不清楚,因此他们将其留给我们来决定和格式化,就像您使用
foreach
语句所做的那样。


11
投票

我同意 mjolinor...只是没有足够的积分来投票...另外我会补充一点,你不需要 GetEnumerator

$ht | out-string | add-content log.txt

会做的。


6
投票

您的第一个示例不起作用,或者更好的是,部分起作用,因为您正在尝试获取字符串中的属性值。通常,在字符串内部,解析器只能解析直接变量(如

$key
)。要解析更复杂的变量,您需要括号。

对于循环,这应该有效:

foreach ($ht.keys 中的 $key) {
添加内容 log.txt "$key : $($ht.$key)" }

甚至更好

$ht.keys | %{ 添加内容 log.txt "$_ : $($ht.$_)" }

6
投票

正如您在 Microsoft 文档中所看到的,哈希表只是名称-值对的集合。

所以

$ht
实际上是由
System.Collections.Hashtable
组成的
System.Collections.DictionaryEntry

一个好的使用方法是

foreach ($i in $ht.keys)
{
  add-content log.txt ("{0} {1}" -f $i, $ht[$i])
}

3
投票

怎么样:

 $ht.GetEnumerator() | Sort-Object Name | out-string | Add-Content log.txt 

0
投票

您可以使用 Out-File 将哈希表的“原始”转储写入 ASCII 文件:

$data = @{
  Name = "Something"
  Type = "123"
}
$data | Out-File "myfile.txt" -Encoding ascii

0
投票

Microsoft 建议在迭代密钥之前先克隆密钥!

这是从 https://learn.microsoft.com/en-us/powershell/scripting/learn/deep-dives/everything-about-hashtable?view=powershell-7.4

复制/粘贴
$environments.Keys.Clone() | ForEach-Object {
    $environments[$_] = 'SrvDev03'
}
© www.soinside.com 2019 - 2024. All rights reserved.