我正在尝试重新格式化我的XML代码,以便更容易阅读。目前它看起来像这样:
<Settings>
<Display_Settings>
<ScreenName Name="1">1</ScreenName>
<ScreenTag Tag="1">1</ScreenTag>
<LocalPosition X="1" Y="1" Z="1">0.000, 0.000, 0.000</LocalPosition>
<Width Width="0.000">0.000</Width>
<Height Height="0.000">0.000</Height>
</Display_Settings>
</Settings>
然而我想要的是这样:
<Settings>
<Display_Settings>
<ScreenName Name="1">1
<ScreenTag Tag="1">1</ScreenTag>
<LocalPosition X="1" Y="1" Z="1">0.000, 0.000, 0.000</LocalPosition>
<Width Width="0.000">0.000</Width>
<Height Height="0.000">0.000</Height>
</ScreenName>
</Display_Settings>
</Settings>
好的,垃圾示例,但我希望你得到这个小说;我希望我的所有值,如标记和本地位置等都是屏幕名称的子项。现在我知道要做到这一点通常是以下的电话:
XmlNode _rootNode; // in the above i'll have set this to be Display_Settings
_rootNode.AppendChild(_screenTag);
但是,我已将我的XML创建代码设置在一个列表中,该列表保存在一个类中并填充在另一个类中。它看起来像这样:
生成XML
public HV_WriteXML()
{
//root node
_rootNode = _xmlDoc.CreateElement("InMo_Settings");
_xmlDoc.AppendChild(_rootNode);
_userNode = _xmlDoc.CreateElement("Display_Settings");
_rootNode.AppendChild(_userNode);
}
public void GenereateSettingsFile(List<Node> nodeList, string filePath)
{
_rootNode.RemoveChild(_userNode);
_userNode = _xmlDoc.CreateElement("Display_Settings");
_rootNode.AppendChild(_userNode);
foreach (Node n in nodeList)
{
foreach (XmlElement e in n.GenerateXML(_xmlDoc))
{
_userNode.AppendChild(e);
}
}
_xmlDoc.Save(filePath);
}
然后为了填补这一点,我在派生类中执行以下操作:
public override List<XmlElement> GenerateXML(XmlDocument _xmlDoc)
{
List<XmlElement> elementList = new List<XmlElement>();
if (nodeDictionary.ContainsKey("Name "))
{
XmlElement _screenName = _xmlDoc.CreateElement("ScreenName");
_screenName.SetAttribute("Name", (string)nodeDictionary["Name "].value);
_screenName.InnerText = (string)nodeDictionary["Name "].value;
elementList.Add(_screenName);
}
if (nodeDictionary.ContainsKey("Tag"))
{
XmlElement _screenTag = _xmlDoc.CreateElement("ScreenTag");
_screenTag.SetAttribute("Tag", (string)nodeDictionary["Tag"].value);
_screenTag.InnerText = (string)nodeDictionary["Tag"].value;
elementList.Add(_screenTag);
}
}
现在我真正的问题是,当我在另一个类的列表中设置我的xml创建时,如何附加我的_screenTag元素以使其成为我的屏幕名称的子项?
答案 0 :(得分:1)
在我看来,您遇到的困难是您的c#数据结构与所需的XML数据结构之间的模式不匹配。
即。您的列表是一个“扁平”结构,但所需的XML已嵌套。
理想情况下,您应该重构代码以使两者更相似,您可以为Display_Settings创建一个c#模型对象,然后根据需要将子属性添加到该类。这可能允许您使用.Net内置的XML序列化,而不必像现在一样手动操作它。
或者,如果您不熟悉手动创建XML,则可以使用XmlElement类中树结构的固有支持,即使用ChildNodes属性:http://msdn.microsoft.com/en-us/library/system.xml.xmlnode.childnodes.aspx
答案 1 :(得分:1)
您可以按照以下方式在XML中的任何位置插入所需的标记
//Get Display_Settings node
XmlNode displaySettingsNode = xmlDoc.SelectSingleNode(@"Settings/Display_Settings");
//Get LocalPosition node
XmlNode screenNameNode = xmlDoc.SelectSingleNode(@"Settings/Display_Settings/LocalPosition");
//Create Screen Tag
XmlElement screenTag = xmlDoc.CreateElement("ScreenTag");
screenTag.SetAttribute("Tag", (string)nodeDictionary["Tag"].value);
screenTag.InnerText = (string)nodeDictionary["Tag"].value;
//Insert Screen Tag node in desired location
displaySettingsNode.InsertBefore(screenTag, screenNameNode);
答案 2 :(得分:0)
这个怎么样? (使用LinqToXml)
var xDoc = XDocument.Parse(xmlstring); //or XDocument.Load(filename)
var elems = xDoc.Descendants("Display_Settings")
.First()
.Elements()
.Where(e => e.Name.LocalName != "ScreenName")
.ToList();
elems.ForEach(e => e.Remove());
xDoc.Descendants("ScreenName").First().Add(elems);
var newxml = xDoc.ToString();