gpt4 book ai didi

powershell - 为什么 PowerShell 在测试长度时默默地将字符串转换为对象 []?

转载 作者:行者123 更新时间:2023-12-03 21:01:58 25 4
gpt4 key购买 nike

Trustedhosts 处理超过 1023 个字符的字符串,而我刚刚突破了这个限制。我正在编写一个不错的小 FILO 队列,以确保我总是可以在需要时添加新主机,并且只有在我发现这种奇怪之处时才省略我最少使用的服务器。我在头发掉光之前就治好了,所以很好。我不明白的是为什么会这样。

$namesString = 'server1.there.com,server2.there.com,server3.there.com'
Write-Host ("So, we have a nice little list of servers. Let's trust them.")
Set-Item wsman:localhost\client\trustedhosts -Value $namesString -Force
Write-Host ("They're nicely trusted now")
if ($namesString.length -gt 1) {
Write-Host ("Now we know it's longish")
}
Write-Host ("OK. Let's try trusting the same string.")
Write-Host ("(By the way, it's a $($namesString.getType()))")
Write-Host ("(and let's check whether it's an array: $($namesString -is [array]))")
Set-Item wsman:localhost\client\trustedhosts -Value $namesString -Force
Write-Host ("Why did testing the length of the string cause this confirmed and tested string to report as an object array?")

结果在以下输出
So, we have a nice little list of servers. Let's trust them.
They're nicely trusted now
Now we know it's longish
OK. Let's try trusting the same string.
(By the way, it's a string)
(and let's check whether it's an array: False)
Set-Item : Cannot convert 'System.Object[]' to the type 'System.String' required by the parameter. Specified method is not sup
ported.
At C:\Users\...\AppData\Local\Temp\2\07da58ce-2578-4603-8291-83e1cc231522.ps1:11 char:9
+ Set-Item <<<< wsman:localhost\client\trustedhosts -Value $namesString -Force
+ CategoryInfo : NotSpecified: (:) [Set-Item], InvalidOperationException
+ FullyQualifiedErrorId : System.InvalidOperationException,Microsoft.PowerShell.Commands.SetItemCommand
Why did testing the length of the string cause this confirmed and tested string to report as an object array?

这个奇怪的东西被埋在 2000 行代码中,有问题的字符串经历了 3 次转换。该字符串每次都将自己报告为字符串,但 wsman 将其拒绝为数组。经过一些严肃的二进制搜索,最终发现它是长度测试静默变成了某种加密数组。

最佳答案

在 PowerShell V1 和 V2 中,当您获取或设置属性或调用成员时,PowerShell 会将值包装在 PSObject 中,以便它可以使用其内部类型适配器来执行操作。

创建这个 PSObject 的成本有点高,所以如果你的对象是一个简单的变量引用,那么 PSObject 就会存储在变量中,这样后续的操作就不会为创建另一个 PSObject 的开销付出代价。

如果这还不清楚,这里有一些例子:

$value = @{ Property = 1 }    # $value is a hashtable

$value.Property # $value is now a PSObject wrapping the hashtable

$value.Property # don't need to create another PSObject

# Under the covers, PowerShell V2 creates a PSObject wrapping the
# string before getting the length, but that PSObject isn't saved anywhere
"hello".Length

PowerShell V3 进行了重大更改以提高性能,并且不再需要这种奇怪的副作用来获得良好的性能。

关于powershell - 为什么 PowerShell 在测试长度时默默地将字符串转换为对象 []?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21860066/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com