c# - 如何使用 Linq to XML 将 XML 转换为嵌套字典?

标签 c# dictionary linq-to-xml

我想将 XML 文件转换为字典。 XML 文件的结构如下。

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<Definitions>   
    <Organization ID="416">
        <Department Name="Facility">
            <Destination Employees="Something" Obj="someObject" Building="none" Type="Int16"\>
        </Department>
    </Organization>
    <Organization ID="502">
        <Department Name="IT">
            <Destination Employees="Something" Obj="someObject" Building="none" Type="Int16"\>
        </Department>
        <Department Name="Specialty">
            <Destination Employees="Something" Obj="someObject" Building="none" Type="Int16"\>
            <Destination Employees="SomethingElse" Obj="someObject" Building="none" Type="Int16"\>
        </Department>
    </Organization> 
</Definitions>

我想使用一个嵌套字典,它可以被概念化为一个表,其中“部门”是行号,“组织”是列号,“员工”、“对象”、“建筑”和“类型”是可以在那里找到的值。因此,我创建了以下类:

// Stores constant data of each tuple <Organization,Department>
public class DatSet
{
    public string Employees { get; set; }
    public string Obj { get; set; }
    public string Building { get; set; }
    public string Type { get; set; }
}

和下面的字典来存储数据:

// Nested Diectionary to allow fast access to XML content
public static Dictionary<int, Dictionary<string, IEnumerable<DatSet>>>;

整棵树表示为 Dictionary<int, Dictionary<string, DatSet>>键是组织 ID,值是字典,键是部门名称,值是数据集。

我想使用以下 LINQ 表达式将 XML 数据转换为嵌套字典。但是,我收到一条错误消息,指出 lambda-expression 无法转换为 System.Collections.Generic.IEqualityComparer 类型(在 org => org.DatSet.ToDictionary(dep => dep.Name)); 中)。

// Converts XML File to nested Dictionary
private static Dictionary<int, Dictionary<string, IEnumerable<DatSet>>> XmlToDict(XDocument element)
{
    return element.Descendants("Organization")
            .Select(org => new
            {
                ID = org.Attribute("ID").Value,
                dep = org.Descendants("Department")
                .Select(dep => new
                {
                    Name = dep.Attribute("Name").Value,
                    DatSet = dep.Descendants("Destination")
                    .Select(dest => new DatSet
                    {
                        Employees = dest.Attribute("Employees").Value,
                        Obj = dest.Attribute("Obj").Value,
                        Building = dest.Attribute("Building").Value,
                        Type = dest.Attribute("Type").Value,
                    })
                })
            })
            .ToDictionary(
                org => int.Parse(org.ID),
                org => org.DatSet.ToDictionary(dep => dep.Name));
}

编辑:

当我按照 ChrFin 的建议更改最后一行时,错误消失了。但是,不,我收到以下 XMLException:

XmlException: Unexpected token. Name is required here. file:///C:/Data/projekt_2/Assets/Resources/DataDef.xml Line 6, position 72.
Mono.Xml2.XmlTextReader.ReadAttributes (Boolean isXmlDecl)
Mono.Xml2.XmlTextReader.ReadStartTag ()
Mono.Xml2.XmlTextReader.ReadContent ()
Mono.Xml2.XmlTextReader.Read ()
System.Xml.XmlTextReader.Read ()
Mono.Xml.XmlFilterReader.Read ()
Mono.Xml.XmlFilterReader.Read ()
System.Xml.Linq.XElement.LoadCore (System.Xml.XmlReader r, LoadOptions options)
System.Xml.Linq.XNode.ReadFrom (System.Xml.XmlReader r, LoadOptions options)
System.Xml.Linq.XContainer.ReadContentFrom (System.Xml.XmlReader reader, LoadOptions options)
System.Xml.Linq.XElement.LoadCore (System.Xml.XmlReader r, LoadOptions options)
System.Xml.Linq.XNode.ReadFrom (System.Xml.XmlReader r, LoadOptions options)
System.Xml.Linq.XContainer.ReadContentFrom (System.Xml.XmlReader reader, LoadOptions options)
System.Xml.Linq.XElement.LoadCore (System.Xml.XmlReader r, LoadOptions options)
System.Xml.Linq.XNode.ReadFrom (System.Xml.XmlReader r, LoadOptions options)
System.Xml.Linq.XContainer.ReadContentFrom (System.Xml.XmlReader reader, LoadOptions options)
System.Xml.Linq.XDocument.ReadContent (System.Xml.XmlReader reader, LoadOptions options)
System.Xml.Linq.XDocument.LoadCore (System.Xml.XmlReader reader, LoadOptions options)
System.Xml.Linq.XDocument.Load (System.String uri, LoadOptions options)
System.Xml.Linq.XDocument.Load (System.String uri)
Input.Awake () (at Assets/Scripts/Input/Input.cs:41)

最佳答案

您需要使用以下内容:

org => org.dep.ToDictionary(dep => dep.Name, dep => dep.DatSet)

这会产生正确的结果 - 请参阅 fiddle .

关于c# - 如何使用 Linq to XML 将 XML 转换为嵌套字典?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25844791/

相关文章:

c# - 如何使用 LINQ 删除没有其子节点的 Xelement?

c# - Expression.Assign 将 Expression.Call 分配给 Expression.Variable

c# - 什么是程序集身份?

javascript - 我如何从中创建 Bootstrap 行? ( react JS)

c# - 如何使用值从字典中删除条目

元素的 c# LINQ to XML 查询表达式是否存在?

c# - 在 C# 中,^ 字符有什么作用?

c# - C# 中 instagram API 中使用的时间戳时间

dictionary - 关键词词典

c# - 我的 LINQ 查询仅返回 1 个结果