LINQ to XML 选择子元素

发布于 2024-08-18 11:10:11 字数 1363 浏览 2 评论 0原文

我正在尝试使用 LINQ to XML 将 XML 文件中的信息提取到对象中。虽然我可以返回文档和部分 Id 属性,但我无法访问每个部分元素的项目,但它返回文档中所有项目的 IEnumerable。我知道这是正确的,因为我正在调用后代,但我正在努力让它只返回每个部分元素的子项。有人可以帮忙吗?

XML 文档

<root>
<document id="1">
  <section id="1.1">
    <item id="1.1.1"></item>
    <item id="1.1.2"></item>
    <item id="1.1.3"></item>
  </section>
  <section id="1.2">
    <item id="1.2.1"></item>
    <item id="1.2.2"></item>
  </section>
</document>
</root>

LINQ 查询

XElement documentRoot = XElement.Load("document.xml");
var documents = (from docs in documentRoot.Descendants("document")
                 select new
                    {
                        Id = (string) docs.Attribute("id"),
                        Sections = docs.Elements("section"),
                        Items = docs.Elements("section").Elements("item")
                    }).ToList();

foreach(var doc in documents)
{
    foreach(var section in doc.Sections)
    {
        Console.WriteLine("SectionId: " + section.Attribute("Id"));  
        foreach(var item in doc.Items)
        {
            Console.WriteLine("ItemId: " + section.Attribute("Id"));
        }
    }
}

I am trying to extract information from an XML file into an object using LINQ to XML. Although I can return the document and section Id attributes I cannot get access to the Items for each section element, it returns an IEnumerable of all the items in the document. I know this is correct as I’m calling Descendants but am struggling to get it to return only the child items of each section element. Can anybody help?

XML Document

<root>
<document id="1">
  <section id="1.1">
    <item id="1.1.1"></item>
    <item id="1.1.2"></item>
    <item id="1.1.3"></item>
  </section>
  <section id="1.2">
    <item id="1.2.1"></item>
    <item id="1.2.2"></item>
  </section>
</document>
</root>

LINQ Query

XElement documentRoot = XElement.Load("document.xml");
var documents = (from docs in documentRoot.Descendants("document")
                 select new
                    {
                        Id = (string) docs.Attribute("id"),
                        Sections = docs.Elements("section"),
                        Items = docs.Elements("section").Elements("item")
                    }).ToList();

foreach(var doc in documents)
{
    foreach(var section in doc.Sections)
    {
        Console.WriteLine("SectionId: " + section.Attribute("Id"));  
        foreach(var item in doc.Items)
        {
            Console.WriteLine("ItemId: " + section.Attribute("Id"));
        }
    }
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

末骤雨初歇 2024-08-25 11:10:11

您在属性 Id 和项目循环上遇到了一些小拼写错误。但是,如果您尝试将所有部分项目放入该项目集合中,那么您在设计级别上就错了,因为 Items 应该是 Section 属性,而不是 Document(因此您需要查询 XML 两次)。

或者,您可以执行以下操作:

var documents =
    (from docs in documentRoot.Descendants("document")
     select new
     {
         Id = (string) docs.Attribute("id"),
         Sections = docs.Elements("section")
     }).ToList();

foreach (var doc in documents)
{
    foreach (var section in doc.Sections)
    {
        Console.WriteLine("SectionId: " + section.Attribute("id"));
        foreach (var item in section.Elements("item"))
        {
            Console.WriteLine("ItemId: " + item.Attribute("id"));
        }
    }
}

输出:

SectionId: id="1.1"
ItemId: id="1.1.1"
ItemId: id="1.1.2"
ItemId: id="1.1.3"
SectionId: id="1.2"
ItemId: id="1.2.1"
ItemId: id="1.2.2"

You got some small typos, on attribute Id and at item loop. But if you're trying to get all section items into that items collection, you're wrong at design level, as Items should be a Section property, not Document (so you'll need to query your XML twice).

Or, you can to do something like:

var documents =
    (from docs in documentRoot.Descendants("document")
     select new
     {
         Id = (string) docs.Attribute("id"),
         Sections = docs.Elements("section")
     }).ToList();

foreach (var doc in documents)
{
    foreach (var section in doc.Sections)
    {
        Console.WriteLine("SectionId: " + section.Attribute("id"));
        foreach (var item in section.Elements("item"))
        {
            Console.WriteLine("ItemId: " + item.Attribute("id"));
        }
    }
}

Output:

SectionId: id="1.1"
ItemId: id="1.1.1"
ItemId: id="1.1.2"
ItemId: id="1.1.3"
SectionId: id="1.2"
ItemId: id="1.2.1"
ItemId: id="1.2.2"
国产ˉ祖宗 2024-08-25 11:10:11

你想要一个扁平结构吗?!?! (来自 LinqPad)

XElement documentRoot  = XElement.Parse (
@"<root> 
<document id='1'> 
  <section id='1.1'> 
    <item id='1.1.1'></item> 
    <item id='1.1.2'></item> 
    <item id='1.1.3'></item> 
  </section> 
  <section id='1.2'> 
    <item id='1.2.1'></item> 
    <item id='1.2.2'></item> 
  </section> 
</document> 
</root> 
");




var documents = (from docs in documentRoot.Descendants("section") 
                 select new 
                    { 
                        SectionId = (string) docs.Attribute("id"), 
                        Items = docs.Elements("item") 
                    }); 
 documents.Dump();

这提供了 2 个 SectionId 项,其中包含具有相关项的 XElement

Do you want a flat structure ?!?! (from LinqPad)

XElement documentRoot  = XElement.Parse (
@"<root> 
<document id='1'> 
  <section id='1.1'> 
    <item id='1.1.1'></item> 
    <item id='1.1.2'></item> 
    <item id='1.1.3'></item> 
  </section> 
  <section id='1.2'> 
    <item id='1.2.1'></item> 
    <item id='1.2.2'></item> 
  </section> 
</document> 
</root> 
");




var documents = (from docs in documentRoot.Descendants("section") 
                 select new 
                    { 
                        SectionId = (string) docs.Attribute("id"), 
                        Items = docs.Elements("item") 
                    }); 
 documents.Dump();

This gives 2 SectionId items that containes XElements with related items.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文