尝试从 XML 文件读取的 C# XML 读取器

本文关键字:XML 读取 文件 | 更新日期: 2023-09-27 18:37:18

我正在尝试从并不总是相同模式的 xml 文件中读取,目标是从文件中读取并将收集的数据排序到 Arrays,以便以后我可以使用排序的数据例如......

XML 文件:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<imgdir name="Eqp.img">
    <imgdir name="Eqp">
        <imgdir name="Accessory">
            <imgdir name="1010000">
                <string name="name" value="Long Brown Beard"/>
            </imgdir>
            <imgdir name="1010001">
                <string name="name" value="Goatee"/>
            </imgdir>
            <imgdir name="1010002">
                <string name="name" value="Ninja Mask for Men"/>
            </imgdir>
            <imgdir name="1010003">
                <string name="name" value="5 O'Clock Shadow"/>
            </imgdir>
            <imgdir name="1010004">
                <string name="name" value="General's Mustache (1)"/>
            </imgdir>
            <imgdir name="1010005">
                <string name="name" value="General's Mustache (2)"/>
            </imgdir>
          </imgdir>
        <imgdir name="Face">
            <imgdir name="1010006">
                <string name="name" value="Yakuza Scar"/>
            </imgdir>
            <imgdir name="1011000">
                <string name="name" value="Ninja Mask for Women"/>
            </imgdir>
            <imgdir name="1011001">
                <string name="name" value="SF Ninja Mask"/>
            </imgdir>
          </imgdir>

这是我的代码

Uri uri = new Uri(path);
string filename = System.IO.Path.GetFileName(uri.LocalPath);
XmlReader reader = XmlReader.Create(path);
int x = 0;
int Row_length = 0;
#region Check Rows Length in File
//===================================================================================================
XmlDocument doc = new XmlDocument();
doc.Load(path);
XmlElement root = doc.DocumentElement;
XmlNodeList elemList = root.GetElementsByTagName("imgdir");
for (x = 0; x < elemList.Count; x++) ;
DisplayChanges_Box.Text += ("Total Elements Count= " + x + ''n' + "XML File= " + filename + ''n');
Row_length = x;
#endregion
int CurrentArrayDataBox = 0;
int[] itemIDArray = new int[x + 1];
string[] itemNamesArray = new string[x + 1];
int LastRow = Row_length;
while (reader.Read())
{
    if (reader.IsStartElement())
    {
        if (reader.HasAttributes)
        {
            //    <<Checking if the current elemnt is a number or Group Name such as Weapons...Gloves...etc>>
            string ItemNumberAsString;
            int ItemNumber;
            string ItemDescription;
            ItemNumberAsString = reader.GetAttribute("name");
            bool parsed = Int32.TryParse(ItemNumberAsString, out ItemNumber);
            if (parsed)
            {
                reader.ReadToNextSibling("string");
                ItemDescription = reader.GetAttribute("string");
                //    <<Write To ID and Names Array the gained data values>>
                itemIDArray[CurrentArrayDataBox] = ItemNumber;
                itemNamesArray[CurrentArrayDataBox] = ItemDescription;
                CurrentArrayDataBox++;
                reader.ReadToFollowing("imgdir");
            }
            else if (!parsed)
            {
                reader.ReadToFollowing("imgdir");
            }
        }
    }
}

====
============该程序应该像这样对信息进行排序...
每次检查当前属性以检测它是否为字符串时,例如:

"Eqp.img"
"Eqp"
"Accessory"

忽略它们
或者如果是

"1010000"
"1010001"
"1010002"
"1010003"
...

将数字存储在ItemIDArray中,并将其"字符串名称"值存储在 ItemNamesArray 中

目前我似乎无法获得数字,仅检测它是否是字符串,当属性为数字时,它将其显示为"名称"而不是实数

真诚的你。

尝试从 XML 文件读取的 C# XML 读取器

以下代码检查 imgdir 节点是否具有字符串子节点。

private bool ReadNameAndValue(XmlNode parent, out string name, out string value)
{
    name = "";
    value = "";
    var node = parent.SelectSingleNode("./string");
    if (node == null)
    {
        return false;
    }
    try
    {
        name = parent.SelectSingleNode("./string/@name").InnerText;
        value = parent.SelectSingleNode("./string/@value").InnerText;
    }
    catch(Exception)
    {
    }
    return true;
}
public void ParseDoc(string fileName = @"c:'temp'soexample.xml")
{
    XmlDocument doc = new XmlDocument();
    doc.Load(fileName);
    var elements = doc.SelectNodes("//imgdir");
    foreach (XmlNode node in elements)
    {
        string name;
        string value;
        if (ReadNameAndValue(node, out name, out value))
        {
            string id = node.SelectSingleNode("./@name").InnerText;
            Console.WriteLine("Id: " + id + ", Name: " + name + ", Value: " + value);
            //do whatever you want with the id, name and value
        }
    }
}

其打印输出是

Id: 1010000, Name: name, Value: Long Brown Beard
Id: 1010001, Name: name, Value: Goatee
Id: 1010002, Name: name, Value: Ninja Mask for Men
Id: 1010003, Name: name, Value: 5 O'Clock Shadow
Id: 1010004, Name: name, Value: General's Mustache (1)
Id: 1010005, Name: name, Value: General's Mustache (2)
Id: 1010006, Name: name, Value: Yakuza Scar
Id: 1011000, Name: name, Value: Ninja Mask for Women
Id: 1011001, Name: name, Value: SF Ninja Mask

正如Jon所建议的,LINQ to XML在这里会简单得多,而且可读性更强。 这是您可以处理它的一种方法:

var doc = XDocument.Load(path);
var items = from imgdir in doc.Descendants("imgdir")
            let name = (string)imgdir.Attribute("name")
            from id in TryParseInteger(name)
            from description in imgdir.Elements("string").Attributes("value").Take(1)
            select new {Id = id, Description = description.Value};

TryParseInteger实现方式如下:

private static IEnumerable<int> TryParseInteger(string value)
{
    int result;
    if (int.TryParse(value, out result))
    {
        yield return result;
    }
}

有关工作示例,请参阅此小提琴。