2017-04-05 71 views
2

此代码:更新数组元素

$test = @" 
<Test> 
    <Child>Hello</Child> 
    <Child>World</Child> 
</Test> 
"@ 

$xml = [xml]$test 
$xml.Test.Child[1] 

收率:

World 

然后,代码:

$xml.Test.Child[1] = "StackOVerflow" 
$xml.InnerXml 

收率:

<Test><Child>Hello</Child><Child>World</Child></Test> 

为什么第二个Child节点没有从World更新为StackOverflow

好吧,让我们尝试不同的东西:

$ipaddress=([System.Net.DNS]::GetHostAddresses($hostname)|Where-Object {$_.AddressFamily -eq "InterNetwork"} | select-object IPAddressToString)[0].IPAddressToString 

现在我不知道的$ipaddress是什么类型:

$ipaddress.GetType() 

IsPublic IsSerial Name          BaseType 
-------- -------- ----          -------- 
True  True  String         System.Object 

显然,这是字符串。

$xml.Test.ChildNodes[1].'#text' = $ipaddress 
Cannot set "#text" because only strings can be used as values to set XmlNode properties. 
At line:1 char:1 
+ $xml.Test.ChildNodes[1].'#text' = $ipaddress 
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 
    + CategoryInfo   : NotSpecified: (:) [], SetValueException 
    + FullyQualifiedErrorId : XmlNodeSetShouldBeAString 

$ipaddress是字符串!

这最后的工作原理:

$xml.Test.ChildNodes[1].'#text' = [string]$ipaddress 

这是怎么回事?

回答

1

似乎与可能已在PowerShell 6中修复的错误有关。我手边没有Linux机器可以检查。

你会找到该bug的说明here

同时,有一种变通方法,因为你已经发现了它:

$test = @" 
<Test> 
    <Child>Hello</Child> 
    <Child>World</Child> 
</Test> 
"@ 

$xml = [xml]$test 
$xml.Test 
$xml.Test.GetType()     # = XmlElement 

$xml.Test.Child[1]      # = World 
$xml.Test.Child[1].GetType()   # = String 

$xml.Test.Child[1] = "Tralala" 
$xml.Test.Child[1]      # = World 


$xml.Test.ChildNodes.Item(1).GetType() # = XmlElement 
$xml.Test.ChildNodes.Item(1)."#text" = "StackOverflow" 
$xml.Test.Child[1]      # = StackOverflow 
+0

在PowerShell中相同的行为6.0.0-alpha.13 –

+0

谢谢你这一点,但你可能已经注意到了,我已经在原始问题本身中发布了相同的工作。 –