Home > Mobile >  C#: Sort xml nodes and childnodes using attribute value
C#: Sort xml nodes and childnodes using attribute value

Time:04-05

Referencing the two questions here and here
I would like to sort on child nodes as well, but resetting for each "outer" node.
So:

<Root>
    <I aa="1">
        <s aa="3"/>
        <s aa="1"/>
        <s aa="2"/>
    </I>
    <I aa="5">
        <s aa="3"/>
        <s aa="1"/>
        <s aa="2"/>
    </I>
    <I aa="3">
        <s aa="3"/>
        <s aa="1"/>
        <s aa="2"/>
    </I>
    <I aa="4">
        <s aa="3"/>
        <s aa="1"/>
        <s aa="2"/>
    </I>
</Root>

Would become:

<Root>
    <I aa="1">
        <s aa="1"/>
        <s aa="2"/>
        <s aa="3"/>
    </I>
    <I aa="3">
        <s aa="1"/>
        <s aa="2"/>
        <s aa="3"/>
    </I>
    <I aa="4">
        <s aa="1"/>
        <s aa="2"/>
        <s aa="3"/>
    </I>
    <I aa="5">
        <s aa="1"/>
        <s aa="2"/>
        <s aa="3"/>
    </I>
</Root>

I tried different variations of the XDocument sorting, but I cannot get the syntax right.
Hoping someone can help, or provide me with an idea.

CodePudding user response:

You need some recursion here - each element needs to be cloned and its child elements sorted by the aa attribute. A method to do that might look like this:

private static XElement CopyAndSort(XElement e)
{
    var elements = e.Elements()
        .OrderBy(x => (string)x.Attribute("aa"))
        .Select(CopyAndSort);
    return new XElement(e.Name, e.Attributes(), elements);
}

If you then call that with your Root element, you will get back a new Root element with all its children sorted (and their children sorted, and so on).

See this fiddle for a working demo.

  • Related