将新的子节点添加到许多父元素 [英] Add new ChildNodes to many parent elements
问题描述
我有一个planets.xml 文件,其中包含3,146 个行星和每个行星的许多子节点.自上周以来,我一直在阅读教程并对其进行测试,试图让它发挥作用,但是,我没有得到它.我只需要知道如何将新的子节点轴"添加到ycoord"节点下的每个父行星"元素中.然后我应该能够为某些行星没有填写的所有其他元素(轨道、压力、水百分比等)复制它.
I have a planets.xml file with 3,146 planets and many childnodes for each planet. I have been reading tutorials and testing it out since last week trying to get this to work but, I am not getting it. I simply need to know how to add a new childnode "axis" into each parent "planet" element under the "ycoord" node. And then I should be able to duplicate that for all the other elements that some planets do not have filled out (orbit, pressure, percentWater, etc).
<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<planets>
<planet>
<name>A Place</name>
<xcood>-123.764</xcood>
<ycood>272.182</ycood>
</planet>
<planet>
<name>Abadan</name>
<xcood>-70.319</xcood>
<ycood>-95.949</ycood>
<pressure>3</pressure>
<gravity>1.03</gravity>
<lifeForm>7</lifeForm>
<climate>2</climate>
<percentWater>63</percentWater>
<temperature>22</temperature>
<spectralClass>F</spectralClass>
<subtype>1</subtype>
<luminosity>V</luminosity>
<sysPos>5</sysPos>
<socioIndustrial>C-C-D-C-C</socioIndustrial>
<landMass>Abadan Major (Abbasid)</landMass>
<landMass>Abadan Minor</landMass>
<landMass>Kuran Major</landMass>
<landMass>Kuran Minor</landMass>
<hpg>B</hpg>
</planet>
<planet>
<name>Abagnar</name>
<xcood>380.231</xcood>
<ycood>314.823</ycood>
<faction>UND</faction>
<factionChange>
<date>2750-01-01</date>
<faction>DC</faction>
</factionChange>
</planet>
</planets>
来自planets.xml的非常短的片段
Very short snip from the planets.xml
我的代码只在列表的最后一个星球上添加新标签.
And my code which is only adding the new tag on the very last planet of the list.
Private Sub btnOK_Click(sender As Object, e As EventArgs) Handles btnOK.Click
Dim xmlPlanets As XmlDocument = New XmlDocument()
xmlPlanets.Load(My.Application.Info.DirectoryPath & "\Planets\planets.xml")
Dim nodePlanets As XmlNodeList = xmlPlanets.GetElementsByTagName("planet")
Dim axis As XmlElement = xmlPlanets.CreateElement("axis")
axis.InnerText = getAxis()
For Each node As XmlNode In nodePlanets
If node.ChildNodes.Equals(axis) Then
Else
node.InsertAfter(axis, node.FirstChild)
End If
Next
Dim orbit As XmlElement = xmlPlanets.CreateElement("orbit")
orbit.InnerText = getOrbit()
xmlPlanets.Save("planets.xml")
Dim pressure As XmlElement = xmlPlanets.CreateElement("pressure")
Dim gravity As XmlElement = xmlPlanets.CreateElement("gravity")
Dim percentWater As XmlElement = xmlPlanets.CreateElement("percentWater")
Dim temperature As XmlElement = xmlPlanets.CreateElement("temperature")
Dim satellite As XmlElement = xmlPlanets.CreateElement("satellite")
Dim writer As XmlTextWriter = New XmlTextWriter("planets.xml", Nothing)
writer.Formatting = Formatting.Indented
xmlPlanets.WriteContentTo(writer)
writer.Flush()
writer.Close()
'Dim readPressure As String = nodePlanets.Item(cbPlanets.SelectedIndex).Item("pressure").InnerText
'txtAtmosphere.Text = getPressure(readPressure)
End Sub
这仅适用于带有 megamek/mekHQ 的个人场景生成器项目.
This is just for a personal scenario generator project with megamek/mekHQ.
推荐答案
我会从 xml 创建一个类.在执行此操作之前,请获取 xml 样本,如上所述,并将轴节点添加到任何一个行星节点.然后在visual studio中,编辑>>将Xml粘贴为类.它将创建您的模型.
I would create a class from the xml. Before you do that, take a sample of the xml, as you have above, and add the axis node to any one of the planet nodes. Then in visual studio, Edit >> Paste Xml as Classes. It will create your model.
XML:
<planets>
<planet>
<name>A Place</name>
<xcood>-123.764</xcood>
<ycood>272.182</ycood>
</planet>
<planet>
<name>Abadan</name>
<xcood>-70.319</xcood>
<ycood>-95.949</ycood>
<axis>some string</axis> <!--added this-->
<pressure>3</pressure>
<gravity>1.03</gravity>
<lifeForm>7</lifeForm>
<climate>2</climate>
<percentWater>63</percentWater>
<temperature>22</temperature>
<spectralClass>F</spectralClass>
<subtype>1</subtype>
<luminosity>V</luminosity>
<sysPos>5</sysPos>
<socioIndustrial>C-C-D-C-C</socioIndustrial>
<landMass>Abadan Major (Abbasid)</landMass>
<landMass>Abadan Minor</landMass>
<landMass>Kuran Major</landMass>
<landMass>Kuran Minor</landMass>
<hpg>B</hpg>
</planet>
<planet>
<name>Abagnar</name>
<xcood>380.231</xcood>
<ycood>314.823</ycood>
<faction>UND</faction>
<factionChange>
<date>2750-01-01</date>
<faction>DC</faction>
</factionChange>
</planet>
</planets>
生成的类:
'''<remarks/>
<System.Xml.Serialization.XmlTypeAttribute(AnonymousType:=True),
System.Xml.Serialization.XmlRootAttribute([Namespace]:="", IsNullable:=False)>
Partial Public Class planets
Private planetField() As planetsPlanet
'''<remarks/>
<System.Xml.Serialization.XmlElementAttribute("planet")>
Public Property planet() As planetsPlanet()
Get
Return Me.planetField
End Get
Set
Me.planetField = Value
End Set
End Property
End Class
'''<remarks/>
<System.Xml.Serialization.XmlTypeAttribute(AnonymousType:=True)>
Partial Public Class planetsPlanet
Private nameField As String
Private xcoodField As Decimal
Private ycoodField As Decimal
Private factionField As String
Private factionChangeField As planetsPlanetFactionChange
Private axisField As String
Private pressureField As Byte
Private pressureFieldSpecified As Boolean
Private gravityField As Decimal
Private gravityFieldSpecified As Boolean
Private lifeFormField As Byte
Private lifeFormFieldSpecified As Boolean
Private climateField As Byte
Private climateFieldSpecified As Boolean
Private percentWaterField As Byte
Private percentWaterFieldSpecified As Boolean
Private temperatureField As Byte
Private temperatureFieldSpecified As Boolean
Private spectralClassField As String
Private subtypeField As Byte
Private subtypeFieldSpecified As Boolean
Private luminosityField As String
Private sysPosField As Byte
Private sysPosFieldSpecified As Boolean
Private socioIndustrialField As String
Private landMassField() As String
Private hpgField As String
'''<remarks/>
Public Property name() As String
Get
Return Me.nameField
End Get
Set
Me.nameField = Value
End Set
End Property
'''<remarks/>
Public Property xcood() As Decimal
Get
Return Me.xcoodField
End Get
Set
Me.xcoodField = Value
End Set
End Property
'''<remarks/>
Public Property ycood() As Decimal
Get
Return Me.ycoodField
End Get
Set
Me.ycoodField = Value
End Set
End Property
'''<remarks/>
Public Property faction() As String
Get
Return Me.factionField
End Get
Set
Me.factionField = Value
End Set
End Property
'''<remarks/>
Public Property factionChange() As planetsPlanetFactionChange
Get
Return Me.factionChangeField
End Get
Set
Me.factionChangeField = Value
End Set
End Property
'''<remarks/>
Public Property axis() As String
Get
Return Me.axisField
End Get
Set
Me.axisField = Value
End Set
End Property
'''<remarks/>
Public Property pressure() As Byte
Get
Return Me.pressureField
End Get
Set
Me.pressureField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property pressureSpecified() As Boolean
Get
Return Me.pressureFieldSpecified
End Get
Set
Me.pressureFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property gravity() As Decimal
Get
Return Me.gravityField
End Get
Set
Me.gravityField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property gravitySpecified() As Boolean
Get
Return Me.gravityFieldSpecified
End Get
Set
Me.gravityFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property lifeForm() As Byte
Get
Return Me.lifeFormField
End Get
Set
Me.lifeFormField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property lifeFormSpecified() As Boolean
Get
Return Me.lifeFormFieldSpecified
End Get
Set
Me.lifeFormFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property climate() As Byte
Get
Return Me.climateField
End Get
Set
Me.climateField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property climateSpecified() As Boolean
Get
Return Me.climateFieldSpecified
End Get
Set
Me.climateFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property percentWater() As Byte
Get
Return Me.percentWaterField
End Get
Set
Me.percentWaterField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property percentWaterSpecified() As Boolean
Get
Return Me.percentWaterFieldSpecified
End Get
Set
Me.percentWaterFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property temperature() As Byte
Get
Return Me.temperatureField
End Get
Set
Me.temperatureField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property temperatureSpecified() As Boolean
Get
Return Me.temperatureFieldSpecified
End Get
Set
Me.temperatureFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property spectralClass() As String
Get
Return Me.spectralClassField
End Get
Set
Me.spectralClassField = Value
End Set
End Property
'''<remarks/>
Public Property subtype() As Byte
Get
Return Me.subtypeField
End Get
Set
Me.subtypeField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property subtypeSpecified() As Boolean
Get
Return Me.subtypeFieldSpecified
End Get
Set
Me.subtypeFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property luminosity() As String
Get
Return Me.luminosityField
End Get
Set
Me.luminosityField = Value
End Set
End Property
'''<remarks/>
Public Property sysPos() As Byte
Get
Return Me.sysPosField
End Get
Set
Me.sysPosField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlIgnoreAttribute()>
Public Property sysPosSpecified() As Boolean
Get
Return Me.sysPosFieldSpecified
End Get
Set
Me.sysPosFieldSpecified = Value
End Set
End Property
'''<remarks/>
Public Property socioIndustrial() As String
Get
Return Me.socioIndustrialField
End Get
Set
Me.socioIndustrialField = Value
End Set
End Property
'''<remarks/>
<System.Xml.Serialization.XmlElementAttribute("landMass")>
Public Property landMass() As String()
Get
Return Me.landMassField
End Get
Set
Me.landMassField = Value
End Set
End Property
'''<remarks/>
Public Property hpg() As String
Get
Return Me.hpgField
End Get
Set
Me.hpgField = Value
End Set
End Property
End Class
'''<remarks/>
<System.Xml.Serialization.XmlTypeAttribute(AnonymousType:=True)>
Partial Public Class planetsPlanetFactionChange
Private dateField As Date
Private factionField As String
'''<remarks/>
<System.Xml.Serialization.XmlElementAttribute(DataType:="date")>
Public Property [date]() As Date
Get
Return Me.dateField
End Get
Set
Me.dateField = Value
End Set
End Property
'''<remarks/>
Public Property faction() As String
Get
Return Me.factionField
End Get
Set
Me.factionField = Value
End Set
End Property
End Class
现在,这个类很容易使用,因为您拥有 .NET 类,而不是尝试导航 xml 文件.我建议使用 xml 序列化将 xml 加载到 .NET 对象中:
Now, this class is very easy to work with because you have .NET classes instead of trying to navigate an xml file. I suggest using xml serialization to load the xml into the .NET object:
Imports System.Xml.Serialization
Imports System.IO
Module Module1
Sub Main()
Dim s As New XmlSerializer(GetType(planets))
Dim p As planets
' load the xml file
Using fs As New FileStream("planets.xml", FileMode.Open)
p = s.Deserialize(fs)
End Using
' operations on the planet objects
For Each planet In p.planet
planet.axis = "new value"
Next
' overwrite the xml file
Using fs As New FileStream("planets.xml", FileMode.Truncate)
s.Serialize(fs, p)
End Using
End Sub
End Module
如您所见,此代码会将每个行星的轴设置为新值".当然,您可以将其设置为任何您想要的值,因为在 for each 循环中您可以访问该星球的所有其他属性.不将它们视为 xml 节点会使它们更易于使用.
As you see, this code will set each planet's axis to "new value". Of course you can set it to whatever you want because in the for each loop you have access to all the other properties of the planet. Not thinking of them as xml nodes makes them much easier to work with.
注意:Visual Studio 的 Paste XML as Classes 很棒,但是如果您的字符串确实应该限制为几个值,那么将它们设为 Enum 是个好主意(如果没有您的干预,生成器不可能知道).您应该修改生成的类或模型,使其更准确地表示您的数据.
Note: Visual Studio's Paste XML as Classes is great, but if you have strings which should really be limited to a few values, it's a good idea to make them Enums (which the generator can't possibly know without your intervention). You should modify the generated classes or model to make it more accurately represent your data.
这篇关于将新的子节点添加到许多父元素的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!