Announcement

Collapse
No announcement yet.

Group By in XSLT 1.1

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Group By in XSLT 1.1

    Guten Morgen!

    Ich hoffe Ihr könnt mir eventuell helfen! Ich sitze nun schon wieder tagelang an einem Problem! Und zwar möchte ich in meinem Stylesheet nach "pname" gruppieren. Leider muss ich auf XSLT 1.1 zurückgreifen was die Sache extrem kompliziert. Ich hatte einen brauchbaren Ansatz für Version 2.0 - der natürlich hinfällig ist, da ich diesen neuen Prozessor nicht zur Verfügung habe!

    Code:
    <xsl:template match="/selection">
     <xsl:for-each-group select="line">
    
    <xsl:value-of select="@pname"/>
    <xsl:value-of select="@holzart"/>
    <xsl:value-of select="@sorte"/>
    <xsl:value-of select="@guete"/>* 
    
    </xsl:for-each>
    </xsl:template>

    Könnt Ihr mir eventuell dabei helfen? Danke für jeden Hinweis!

    Hier noch die Struktur meines XML Docs:

    Code:
    <?xml version="1.0" encoding="iso-8859-1"?>
    <selection>
        <line auftrag="HFK06009 Poschinger" waldbesitzer="Frhr. von Poschinger" spediteur="" ziel="" pname="158" holzart="Fi" sorte="ISK" guete="" laenge="2.0" stueck="" menge="13.930" lmenge="9.035" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="HFK08009" waldbesitzer="Wiedemann, Wilhelm" spediteur="Frei Wald" ziel="Aichinger Matthias" pname="51" holzart="Fi" sorte="PAL" guete="D" laenge="4.0" stueck="10" menge="2.640" lmenge="2.640" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="HJM05028 Einschlag" waldbesitzer="FC" spediteur="Vincent" ziel="SRA" pname="HJM/1" holzart="Ta" sorte="Lh" guete="" laenge="18.0" stueck="" menge="386.000" lmenge="35.000" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="HJM05028 Einschlag" waldbesitzer="FC" spediteur="Vincent" ziel="SRA" pname="HJM/1" holzart="Ta" sorte="Lh" guete="" laenge="18.0" stueck="" menge="386.000" lmenge="386.000" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="HJM06046 Holzernte" waldbesitzer="" spediteur="Kuhn, Edmund Transp." ziel="SE Maxau" pname="P19" holzart="Fi" sorte="ISN" guete="" laenge="4.0" stueck="" menge="19.500" lmenge="19.500" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="HW08RPI022" waldbesitzer="" spediteur="Salokat" ziel="SE Maxau" pname="7" holzart="Fi" sorte="ISN" guete="" laenge="3.0" stueck="" menge="6.318" lmenge="5.940" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="JGB07028" waldbesitzer="" spediteur="Lecaillié, Michel" ziel="SE Ybbs" pname="4" holzart="Fi" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="275.000" lmenge="50.000" waldlager="225.000" restmenge=""/>
        <line auftrag="JGB07028" waldbesitzer="" spediteur="Lecaillié, Michel" ziel="SE Ybbs" pname="4" holzart="Fi" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="275.000" lmenge="52.000" waldlager="223.000" restmenge=""/>
        <line auftrag="JGB07028" waldbesitzer="" spediteur="Lecaillié, Michel" ziel="SE Ybbs" pname="4" holzart="Fi" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="275.000" lmenge="52.000" waldlager="223.000" restmenge=""/>
        <line auftrag="JGB07028" waldbesitzer="" spediteur="Lecaillié, Michel" ziel="SE Ybbs" pname="4" holzart="Fi" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="275.000" lmenge="26.000" waldlager="249.000" restmenge=""/>
        <line auftrag="KBF07003A" waldbesitzer="FBV Günterod/Kisselherke" spediteur="Frei Wald" ziel="Krappen GmbH &amp; Co. KG" pname="456" holzart="Dgl" sorte="Abs" guete="B/C" laenge="4.1" stueck="" menge="24.610" lmenge="24.609" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="KBF07010C" waldbesitzer="" spediteur="Werner, Hans-Joachim" ziel="SE Kabel" pname="9" holzart="Fi" sorte="ISN" guete="" laenge="2.0" stueck="" menge="124.800" lmenge="6.384" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="KBF07010C" waldbesitzer="" spediteur="Werner, Hans-Joachim" ziel="SE Kabel" pname="9" holzart="Fi" sorte="ISN" guete="" laenge="2.0" stueck="" menge="124.800" lmenge="19.200" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="KBF07010C" waldbesitzer="" spediteur="Werner, Hans-Joachim" ziel="SE Kabel" pname="9" holzart="Fi" sorte="ISN" guete="" laenge="2.0" stueck="" menge="124.800" lmenge="34.248" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="KBF07010C" waldbesitzer="" spediteur="Werner, Hans-Joachim" ziel="SE Kabel" pname="9" holzart="Fi" sorte="ISN" guete="" laenge="2.0" stueck="" menge="124.800" lmenge="33.192" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="KBF07010C" waldbesitzer="" spediteur="Werner, Hans-Joachim" ziel="SE Kabel" pname="9" holzart="Fi" sorte="ISN" guete="" laenge="2.0" stueck="" menge="124.800" lmenge="32.880" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="RRS06018A" waldbesitzer="Rester" spediteur="Meyer Gebr" ziel="SE Maxau" pname="307" holzart="Fi" sorte="ISN" guete="" laenge="3.0" stueck="" menge="6.050" lmenge="9.600" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="RRS07003A" waldbesitzer="" spediteur="Meyer Gebr" ziel="H.A.S.E. Hermeskeil" pname="26" holzart="Ndh" sorte="PAL" guete="C/D" laenge="2.4" stueck="" menge="13.020" lmenge="13.000" waldlager="Abgefahren" restmenge="0.000"/>
        <line auftrag="RRS07012A" waldbesitzer="" spediteur="Walter, Robin Int. Sped." ziel="Karl Decker GmbH" pname="17" holzart="Dgl" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="18.220" lmenge="16.744" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="RRS07012A" waldbesitzer="" spediteur="Walter, Robin Int. Sped." ziel="Karl Decker GmbH" pname="17" holzart="Dgl" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="18.220" lmenge="41.860" waldlager="Abgefahren" restmenge=""/>
        <line auftrag="RRS07012A" waldbesitzer="" spediteur="" ziel="" pname="17" holzart="Dgl" sorte="Abs" guete="B/C" laenge="4.0" stueck="" menge="18.220" lmenge="0.010" waldlager="Abgefahren" restmenge="0.000"/>
    </selection>
    Gruss, FreezerSE
    Zuletzt editiert von FreezerSE; 26.09.2008, 09:25.

  • #2
    Ansatz (gibt zu jeder pname-Attribut-Gruppe eine Liste der Aufträge aus):
    Code:
    <?xml version="1.0" encoding="ISO-8859-1"?>
    <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    
      <xsl:key name="groupby" match="line" use="@pname"/>
    
      <xsl:template match="selection">
    
        <xsl:for-each select="line[generate-id() = generate-id(key('groupby',@pname)[1])]">
    
          <p><xsl:value-of select="@pname"/></p>
          <ul><xsl:for-each select="key('groupby',@pname)">
            <li><xsl:value-of select="@auftrag"/></li>
          </xsl:for-each></ul>
    
        </xsl:for-each>
    
      </xsl:template>
    
    </xsl:stylesheet>
    Zuletzt editiert von Thomas Meinike; 26.09.2008, 09:02.

    Comment


    • #3
      Hallo Thomas! Habe Deinen Rat befolgt und den Code reduziert.

      Ich habe bereits einiges gelesen und folgendes ausprobiert, hatte allerdings keinen Erfolg dabei:

      <xsl:template match="selection">
      <xsl:key name="group-pname" match="line" use="@pname" />
      <xsl:for-each select="line[count(. | key('group-pname', @pname)[1]) = 1]">
      <xsl:sort select="@pname" />
      <xsl:value-of select="@pname" />
      <xsl:value-of select="@holzart" />
      <xsl:value-of select="@sorte" />
      <xsl:value-of select="@guete" />
      </xsl:for-each>
      </xsl:template>

      Ist der Code tatsächlich so falsch oder geht es schon in die richtige Richtung? Sieht für mich schon ganz okay aus! Würde mich freuen, wenn Du Dich der Sache nochmal annehmen könntest! Mein Learning-by-Doing ist zugegeben etwas schleppend, so ganz ohne Expertenrat!

      Vielen Dank und Gruss,

      FreezerSE

      Comment


      • #4
        Siehe meine zuvor erweiterte Antwort.

        Comment


        • #5
          Hallo Thomas! Vielen Dank für Deinen Post!

          Leider funktioniert es noch nicht! Der HTML Bericht wird einfach nicht generiert!
          Ich gucke es mir später an ob ich noch einen Fehler finden kann! Schade!

          Gruss, FreezerSE

          Comment


          • #6
            So, ich habe es jetzt hinbekommen, dass der Bericht generiert wird! Allerdings ist der Output noch nicht so wie ich es mir vorstelle! Und zwar werden weiterhin alle Informationen mehrfach angezeigt! Die Gruppierung von pname sollte eigentlich dazu führen, dass immer nur eine Zeile für den jeweiligen "pname" angezeigt wird! Kann man die Gruppierung irgendwie erweitern um nur noch einen "pname" anzeigen zu lassen auch wenn das XML File n Zeilen dafür hat!?

            Beispiel:

            Die folgenden Zeilen sollen nur noch einmal angezeigt werden im Stylesheet:

            Code:
            <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="35.556" waldlager="Abgefahren" restmenge=""/>
                <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="20.100" waldlager="Abgefahren" restmenge=""/>
                <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="37.596" waldlager="Abgefahren" restmenge=""/>
                <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="38.148" waldlager="Abgefahren" restmenge=""/>
                <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="25.404" waldlager="Abgefahren" restmenge="0.000"/>
                <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="36.144" waldlager="Abgefahren" restmenge=""/>
                <line auftrag="SJT07004A" waldbesitzer="Schroeder" spediteur="Eickelmann Transporte" ziel="NL Duisburg" pname="75" holzart="Fi" sorte="Abs" guete="B/C" laenge="3.2" stueck="0" menge="238.880" lmenge="36.552" waldlager="Abgefahren" restmenge=""/>
            Gibt es dafür eine Möglichkeit? Kann man die Gruppierung erweitern?

            Comment


            • #7
              Ist ohne den XSLT-Code nicht nachvollziehbar, aber vermutlich reicht das jeweilige Abfragen mittels line[1] pro Gruppe.

              Comment


              • #8
                Hallo Thomas! Danke für Dein Feedback!

                Der Code lautet wie folgt:

                Code:
                <xsl:key name="groupby" match="line" use="@pname"/>
                <xsl:key name="sorte-and-guete-and-einheit" match="polter" use="concat(sortierung,':',guete,':',emenge)"/>
                <xsl:key name="sorte" match="polter" use="sortierung"/>
                <xsl:key name="Fm" match="polter" use="emenge[emenge='Fm']"/>
                
                <xsl:template match="/selection">
                
                <?xml version="1.0" encoding="iso-8859-1" ?>
                <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
                
                <xsl:for-each select="line[generate-id() = generate-id(key('groupby',@pname)[1])]">
                
                <xsl:for-each select="key('groupby',@pname)">
                
                <xsl:value-of select="@pname"/>
                <xsl:value-of select="@holzart"/>
                <xsl:value-of select="@sorte"/>
                <xsl:value-of select="@guete"/>
                
                </xsl:for-each>
                </xsl:for-each>
                </xsl:for-each>
                
                </xsl:template>
                	
                </xsl:stylesheet>
                Wie wird die Abfrage mittels line[1] pro Gruppe bewältigt?

                Code:
                <xsl:for-each select="line[1]">
                ist nicht der richtige Ansatz!

                Sorry für die stupiden Anfängerfragen aber ich bin noch etwas unbeholfen auf dem Gebiet wenn es zu mehr kommt als dem Auslesen der einzelnen Nodes!

                Gruss,

                Sebastian

                Comment


                • #9
                  Seltsames, fehlerhaftes Stylesheet ...

                  Bezogen auf meine erste Antwort mittels Abfrage von position() = 1:
                  Code:
                  <?xml version="1.0" encoding="ISO-8859-1"?>
                  <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
                  
                    <xsl:key name="groupby" match="line" use="@pname"/>
                  
                    <xsl:template match="selection">
                  
                      <xsl:for-each select="line[generate-id() = generate-id(key('groupby',@pname)[1])]">
                  
                        <p><xsl:value-of select="@pname"/></p>
                        <ul><xsl:for-each select="key('groupby',@pname)">
                          <xsl:if test="position() = 1">
                          <li><xsl:value-of select="@auftrag"/></li>
                          </xsl:if>        
                        </xsl:for-each></ul>
                  
                      </xsl:for-each>
                  
                    </xsl:template>
                  
                  </xsl:stylesheet>

                  Comment


                  • #10
                    Guten Abend Thomas!

                    Zu allererst einmal vielen Dankk für Deine Erklärung! Ich habe es nun genau so hinbekommen wie ich es mir vorgestellt hatte! Das Stylesheet hatte ich in Eile gekürzt und dabei etwas verunstaltet! Entschuldigung falls es irreführend war!

                    Ich habe leider noch eine weitere Frage! Und zwar muss ich die Summe von "@menge" über alle Gruppen bilden! Mein Problem besteht darin, dass die "menge" in n Zeilen vorkommt und bei der Summenbildung zu einer vollkommen falschen Summe führt. Für jede Gruppe darf nur einmal die "menge" addiert werden! Ist das irgendwie möglich?

                    Die Summierung der "lmenge" für jede Gruppe habe ich durch den Verweis auf die pguid realisiert. Bsp.: sum(//line/[@pguid=$pguid]/@lmenge)

                    Gibt es eine Möglichkeit meine Frage auf ähnliche Weise zu lösen? Indem z.Bsp. immer nur die erste Zeile jeder Gruppe @menge summiert wird?

                    Vielleicht hast Du noch Zeit und eine Idee? Falls nicht, danke ich Dir trotzdem vielmals für Deine Hilfe bis hierher! Du bist mir eine große Hilfe gewesen (auch in meinen anderen Posts)! Danke!

                    Gruss,
                    Sebastian

                    Comment


                    • #11
                      Unter Bezugnahme auf das Attribut menge der jeweils ersten gruppierten Zeile:
                      Code:
                      <xsl:value-of select="sum(line[generate-id() = generate-id(key('groupby',@pname)[1])]/@menge)"/>
                      erhalte ich mit dem genannten Beispielcode das Ergebnis 998.958.

                      Comment


                      • #12
                        Danke Thomas! Ist echt genial wie einfach Du diese Sachen aus dem Ärmel schüttelst! Woher hast Du nur das Wissen? Gibt es eine bestimmte Must-Read Lektüre?

                        Mein Ansatz war <xsl:value-of select="sum(//line[@pguid=$pguid][1]/@menge)"/> wobei ich davon wiederum die Summe hätte bilden müssen!

                        Jetzt wo ich mir Dein Beispiel angesehen habe, ist mir auch die Vorgehensweise etwas klarer:

                        Du gruppierst nur die ersten Knoten jeder Gruppe und bildest darüber die Summe, richtig?

                        Ich habe die Gruppierung nach pname zu pguid verändert, da pname nicht eindeutig sein muss! Ich danke Dir also abermals für Deine Hilfe und hoffe irgendwann auch jemandem helfen zu können anstatt immer nur Fragen zu stellen!?

                        Mit besten Grüßen und noch einen erfolgreichen Tag,

                        Sebastian

                        Comment


                        • #13
                          Einen guten Einstieg bietet nach wie vor der XML-Darstellungsteil von SELFHTML. Das High-End-Buch stammt von Michael Kay, welches allerding kein reines Lehrbuch sondern mehr ein Nachschlagewerk ist.
                          Zuletzt editiert von Thomas Meinike; 30.09.2008, 14:00.

                          Comment

                          Working...
                          X