Мне нужно l oop - XML, создать новый элемент со значениями из существующих элементов, а затем удалить существующие элементы. Я сделал это довольно далеко, и он работает, как и ожидалось, для первого l oop, но некоторые части выходят из строя в последующих циклах. Надеюсь, что кто-то может взглянуть и дать направление, поскольку я исчерпал свои тонкие знания PowerShell. Вот пример начала XML. Обратите внимание, что элемент может быть вложен непоследовательно:
<val:root xmlns:val="urn:dummy">
<bla>foo</bla>
<value>
<sometag>foo</sometag>
<displayx>1x</displayx>
<displayy>1y</displayy>
<displaywidth>1w</displaywidth>
<displayheight>1h</displayheight>
<someothertag>foo</someothertag>
</value>
<value>
<sometag>foo</sometag>
<displayx>2x</displayx>
<displayy>2y</displayy>
<someothertag>foo</someothertag>
<yetanothertag>foo</yetanothertag>
</value>
<nest>
<value>
<displayx>3x</displayx>
<displayy>3y</displayy>
<displaywidth>3w</displaywidth>
<displayheight>3h</displayheight>
<someothertag>foo</someothertag>
</value>
</nest>
</val:root>
Когда выполняется, вот вывод:
<val:root xmlns:val="urn:dummy">
<bla>foo</bla>
<value>
<sometag>foo</sometag>
<someothertag>foo</someothertag>
<display x="1x" y="1y" w="1w" h="1h" />
</value>
<value>
<sometag>foo</sometag>
<someothertag>foo</someothertag>
<yetanothertag>foo</yetanothertag>
<display x="" y="" />
</value>
<nest>
<value>
<someothertag>foo</someothertag>
</value>
</nest>
</val:root>
Первый узел идеален. Значения существующих элементов отображения были добавлены в новый элемент в качестве атрибутов. Последующие элементы значений не являются захватывающими значениями, а третий (вложенный) даже не создал новый элемент.
Вот текущий скрипт:
# Define the document
$filename = "2.xml";
# Read Content
$xml = [System.Xml.XmlDocument](Get-Content (Resolve-Path $fileName));
$nodes = $xml.SelectNodes("*/value")
#$nodes = $xml.root.value
# Loop through each <value> element, capture <display*> values, write values to new element as attributes
foreach ($v in $nodes) {
# Create new element
$newDisplay = $v.AppendChild($xml.CreateElement("display"));
# Collect existing x value and write as attribute
$x = $v.displayx
$newDisplay.SetAttribute("x","$x");
# Collect existing y value and write as attribute
$y = $v.displayy
$newDisplay.SetAttribute("y","$y");
# Collect existing w value, if available, and write as attribute
$w = $v.displaywidth
if($v.displaywidth -ne $null) {
$newDisplay.SetAttribute("w","$w");
}
# Collect existing w value, if available, and write as attribute
$h = $v.displayheight
if($v.displayheight -ne $null) {
$newDisplay.SetAttribute("h","$h");
}
# Delete old elements
$node = $xml.SelectSingleNode("//displayx")
while ($node -ne $null)
{
$node.ParentNode.RemoveChild($node)
$node = $xml.SelectSingleNode("//displayx")
}
$node = $xml.SelectSingleNode("//displayy")
while ($node -ne $null)
{
$node.ParentNode.RemoveChild($node)
$node = $xml.SelectSingleNode("//displayy")
}
$node = $xml.SelectSingleNode("//displaywidth")
while ($node -ne $null)
{
$node.ParentNode.RemoveChild($node)
$node = $xml.SelectSingleNode("//displaywidth")
}
$node = $xml.SelectSingleNode("//displayheight")
while ($node -ne $null)
{
$node.ParentNode.RemoveChild($node)
$node = $xml.SelectSingleNode("//displayheight")
}
}
# Save
$xml.Save((Resolve-Path $filename));
Ширина и элементы height являются необязательными, поэтому для них используются операторы if.
Очевидно, что это связано с тем, как он собирает информацию и выполняет циклы, но здесь я мог бы использовать некоторую помощь. Я уверен, что способ удаления узлов также может быть чище ...
Заранее спасибо.