2012-11-02 13 views
5

I mają następujące sprawy związane z XPATH1 i XPATH2:XPath 1 i XPath 2 powrotne różne wyniki przy określaniu wartości min i max

<document> 
    <val>3</val> 
    <val>11</val> 
    <val>3</val> 
    <val>2</val> 
    <val>12</val> 
    <val>5</val> 
    <val>0</val> 
    <val>7</val> 
</document> 

xpath1: max

//val[not(. < //val)] 

min:

//val[not(. > //val)] 

xpath2:

document/val[. = max(//val)] 

document/val[. = min(//val)] 

Dlaczego nie mogę uzyskać ten sam rezultat w przetwórstwie XPATH2 z kwerendy xpath1-max:

//val[not(. < //val)] 

Wydaje się, że ostatni węzeł (z val 7), ale nie jest najwyższą wartością. .. na odwrót dla wartości MIN współpracuje z przetwarzaniem XPATH2:

//val[not(. > //val)] 

Czy ktoś może mi pomóc tam?

Odpowiedz

5

Bardzo dobry punkt.

W ścieżce xpath 1 (i xslt 1.0), //val[not(. < //val)] z natury rzuca wartości tekstowe na liczby i wykonuje porównanie na liczbach.

Otrzymujesz poprawne wartości min i maks.

Jednak w ścieżce xpath 2 (i xslt 2.0) tekst nie jest rzutowany na numeryczne, a zamiast tego wykonywane jest porównywanie ciągów znaków. Używając porównania łańcuchów, "7" wynosi> "12", a zatem 7 nadal będzie najwyższą wartością (nie zwraca ostatniej wartości z listy - spróbuj zmienić kolejność wartości).

Co z tego? powinieneś zrobić, aby być bezpiecznym zarówno w xslt 1 jak i 2, należy użyć number() function do obsadzenia tekstu, aby upewnić się, że dokonano porównania numerycznego.

Max:

//val[not(number(.) &lt; //val)] 

min:

//val[not(number(.) &gt; //val)] 

Korzystanie Saxon z arkusza stylów:

<?xml version="1.0" encoding="UTF-8"?> 
<xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 

    <xsl:output method="xml" indent="yes"/> 

    <xsl:template match="/"> 
     <x> 
      <Max1> 
       <xsl:value-of select="//val[not(number(.) &lt; //val)]" /> 
      </Max1> 
      <Min1> 
       <xsl:value-of select="//val[not(number(.) &gt; //val)]" /> 
      </Min1> 
      <Max2> 
       <xsl:value-of select="/document/val[. = max(//val/text())]" /> 
      </Max2> 
      <Min2> 
       <xsl:value-of select="/document/val[. = min(//val/text())]" /> 
      </Min2> 
     </x> 
    </xsl:template> 
</xsl:stylesheet> 

Zwraca

<x> 
    <Max1>12</Max1> 
    <Min1>0</Min1> 
    <Max2>12</Max2> 
    <Min2>0</Min2> 
</x> 

zgodnie z oczekiwaniami.

+2

wow, bardzo ładne wyjaśnienie; dziękuję bardzo, że pomaga mi! – Fl0R1D3R