在.Net中使用XPath对XML进行排序

时间:2018-10-10 18:40:34

标签: vb.net xpath

我正在尝试从以下列表中检索最新的“最终”记录:

pathMappings

该数据应该只有一个“最终”状态条目,我编写了代码以简单地找到该条目。但是我们发现实际数据充满了这样的多个“最终”。所以我需要得到日期最高的那个。

我看到这是possible using Xpath,这就是我已经处理解析的方式,但是我不知道如何将其转换为VB.Net代码。有人有摘要吗?

3 个答案:

答案 0 :(得分:1)

这是做到这一点的一种方式

    Dim myxml As String = "<StatusRecords><Status><Name>final</Name><Date>1/1/2006</Date></Status><Status><Name>final</Name><Date>1/1/2010</Date></Status><Status><Name>interim</Name><Date>1/1/2005</Date></Status></StatusRecords>"
    Dim xp As XPathDocument = New XPathDocument(New StringReader(myxml.ToString))
    Dim xn As XPathNavigator = xp.CreateNavigator
    Dim xi As XPathNodeIterator = xn.Select("//StatusRecords/Status")
    Dim thedate As Date = "1/1/1900" 
    Dim loopdate As Date
    Dim maxfinal As String = "?"
    Do While xi.MoveNext
        loopdate = CDate(xi.Current.SelectSingleNode("Date").InnerXml)
        If loopdate > thedate Then
            thedate = loopdate
            maxfinal = xi.Current.SelectSingleNode("Name").InnerXml
        End If
    Loop
    Response.Write(maxfinal & ":" & thedate.ToShortDateString)

输出为

final:1/1/2010

答案 1 :(得分:0)

如果没有通过XSL,则可以使用LINQ-to-XML获取数据,如下所示:

Module Module1

    Sub Main()
        Dim x = <StatusRecords>
                    <Status>
                        <Name>final</Name>
                        <Date>1/1/2006</Date>
                    </Status>
                    <Status>
                        <Name>final</Name>
                        <Date>1/1/2010</Date>
                    </Status>
                    <Status>
                        <Name>interim</Name>
                        <Date>1/1/2005</Date>
                    </Status>
                </StatusRecords>

        Dim ci = Globalization.CultureInfo.GetCultureInfo("en-US")

        Dim y = x...<Status>.<Date>.Max(Function(d) DateTime.Parse(d.Value, ci))

        Dim z = x...<Status>.First(Function(s) DateTime.Parse(s.<Date>.Value, ci) = y)

        Console.WriteLine("Latest date: " & y.ToString("yyyy-MM-dd"))
        Console.WriteLine(z)

        Console.ReadLine()

    End Sub

End Module

输出:

Latest date: 2010-01-01
<Status>
  <Name>final</Name>
  <Date>1/1/2010</Date>
</Status>

答案 2 :(得分:0)

TonyE的上述评论最终是解决此问题的关键。问题是您需要将日期转换为数字,然后对该数字使用max。结果很混乱,但似乎可以正常工作:

/StatusRecords/Status[number(concat(substring(Date, 1, 4),substring(Date, 6,2),substring(Date, 9, 2),substring(Date, 12, 2),substring(Date, 15, 2),substring(Date, 18, 2)))=max(/StatusRecords/Status/number(concat(substring(Date, 1, 4),substring(Date, 6,2),substring(Date, 9, 2),substring(Date, 12, 2),substring(Date, 15, 2),substring(Date, 18, 2))))]

我怀疑有一种更简单,更紧凑的格式,但是工作是一种功能。谢谢托尼!

更新:原来也需要hms部分。