【问题标题】:Sorting of XContainer based on attribute valueXContainer根据属性值排序
【发布时间】:2018-11-22 08:06:56
【问题描述】:

谁能帮我根据属性值对 XmlDocument 进行排序。

我给出了一个包含几个 attr 元素的示例 xml。因此,我想根据具有属性 Name="from" 的元素的“值”属性对其进行排序,我正在尝试使用 linq to xml 来实现这一点。

这是我尝试过的一个示例代码。但它只保留排序顺序的“来自”属性。我想要在预期的 xml 下的所有属性,如下所示。

container.ReplaceNodes(
            from childEl in container.Elements().Elements()
            where childEl.Attribute("Name")?.Value == "from"
            orderby childEl.Attribute("Value")?.Value descending
            select childEl
        );
        foreach (XElement childEl in container.Elements().Where(e => e.HasElements))
    {
        SortByName(childEl);
    }

输入 XML:

`<Attrs>
  <Attr Name="zddressprevious" isVerified="false">
    <Attr Name="from" Value="2014-01-01" isVerified="false" />
    <Attr Name="house" Value="3" isVerified="false" />
    <Attr Name="street" Value="Test Street" isVerified="false" />
  </Attr>
  <Attr Name="addressprevious" isVerified="false">
    <Attr Name="from" Value="2015-01-01" isVerified="false" />
    <Attr Name="house" Value="1" isVerified="false" />
    <Attr Name="street" Value="Acacia Avenue" isVerified="false" />
  </Attr>
  <Attr Name="addressprevious" isVerified="false">
    <Attr Name="from" Value="2016-01-01" isVerified="false" />
    <Attr Name="house" Value="1" isVerified="false" />
    <Attr Name="street" Value="Test Street" isVerified="false" />
   </Attr>
</Attrs>`

预期输出:

`<?xml version="1.0" encoding="utf-8"?>
<Attrs>
  <Attr <Attr Name="addressprevious" isVerified="false">
    <Attr Name="from" Value="2016-01-01" isVerified="false" />
    <Attr Name="house" Value="1" isVerified="false" />
    <Attr Name="street" Value="Test Street" isVerified="false" />
   </Attr>
   <Attr Name="addressprevious" isVerified="false">
    <Attr Name="from" Value="2015-01-01" isVerified="false" />
    <Attr Name="house" Value="1" isVerified="false" />
    <Attr Name="street" Value="Acacia Avenue" isVerified="false" />
  </Attr>
  <Attr Name="zddressprevious" isVerified="false">
    <Attr Name="from" Value="2014-01-01" isVerified="false" />
    <Attr Name="house" Value="3" isVerified="false" />
    <Attr Name="street" Value="Test Street" isVerified="false" />
  </Attr>
</Attrs>`

【问题讨论】:

    标签: c# linq-to-xml


    【解决方案1】:

    您的LINQ 语句必须通过childEl.Parent 返回父元素(包含来自属性的元素)。

    从您的问题来看,您的容器是XDocument 还是XElement 并不完全清楚。

    如果是 XElementLINQstatement 看起来像:

    var q =
        from childEl in container.Elements("Attr").Elements("Attr")                
        where childEl.Attribute("Name")?.Value == "from"
        orderby childEl.Attribute("Value")?.Value descending
        select childEl.Parent
        ;
    

    替换为:

    container.ReplaceNodes(q);
    

    请注意,LINQ 语句没有明确指定 Attr元素名称也可以完成这项工作:

    var q =
        from childEl in container.Elements().Elements()                
        where childEl.Attribute("Name")?.Value == "from"
        orderby childEl.Attribute("Value")?.Value descending
        select childEl.Parent
        ;
    



    如果是 XDocument,您的查询必须如下所示:

    var q =
        from childEl in container.Element("Attrs").Elements("Attr").Elements("Attr")                
        where childEl.Attribute("Name")?.Value == "from"
        orderby childEl.Attribute("Value")?.Value descending
        select childEl.Parent
        ;
    

    你必须通过以下方式替换节点:

    container.Element("Attrs").ReplaceAll(q);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-08-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-01-29
      • 2017-04-06
      • 1970-01-01
      相关资源
      最近更新 更多