How to fix this elimination on successive node appearance using XSLT?

iwannabegood

New Member
I have this input file:\[code\]<myroot> <list id="xxx"> <node id="a"> <section id="i"> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> <item1 id="a0" method="start"> <!-- this one is successive from the previous so we eliminate --> <somechild>a</somechild> </item1> <item1 id="a0" method="stop"/> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> </section> <section id="i"> <item1 id="a0" method="start"> <!-- this one is successive from the previous so we eliminate --> <somechild>a</somechild> </item1> <item1 id="a0" method="stop"/> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> <item1 id="a0" method="start"> <!-- this one is successive from the previous so we eliminate --> <somechild>a</somechild> </item1> </section> </node> </list></myroot>\[/code\]And my output:\[code\] <myroot> <list id="xxx"> <node id="a"> <section id="i"> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> <item1 id="a0" method="stop"/> </section> <section id="i" /> </node> </list> </myroot>**While the expected output should be:**<myroot> <list id="xxx"> <node id="a"> <section id="i"> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> <item1 id="a0" method="stop"/> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> </section> <section id="i"> <item1 id="a0" method="stop"/> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> </section> </node> </list></myroot>\[/code\]XSLT file:\[code\]<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> <xsl:strip-space elements="*"/> <xsl:output indent="yes"/> <xsl:template match="@* | node()" name="identity"> <xsl:copy> <xsl:apply-templates select="@* , node()"/> </xsl:copy> </xsl:template> <xsl:template match="/*/*/*"> <xsl:copy> <xsl:variable name="first-in-group" as="element()*"> <xsl:for-each-group select="*" group-by="concat(node-name(.), '|', @id,'|', @method)"> <xsl:for-each-group select="current-group()/*" group-by="concat(@id, '|', @method)"> <xsl:sequence select="for $pos in 1 to count(current-group()) return current-group()[$pos] [every $item in subsequence(current-group(), 1, $pos - 1) satisfies not(deep-equal($item, current-group()[$pos]))] "/> </xsl:for-each-group> </xsl:for-each-group> </xsl:variable> <xsl:apply-templates select="@*"/> <xsl:apply-templates> <xsl:with-param name="first-in-group" select="$first-in-group" tunnel="yes"/> </xsl:apply-templates> </xsl:copy> </xsl:template> <xsl:template match="/*/*/*/*/*"> <xsl:param name="first-in-group" tunnel="yes"/> <xsl:if test="$first-in-group intersect ."> <xsl:call-template name="identity"/> </xsl:if> </xsl:template></xsl:stylesheet>\[/code\]Another scenario:\[code\]<myroot> <list id="xxx"> <node id="a"> <section id="i"> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> </section> <section id="i"> <item1 id="a1" method="start"> <somechild>a</somechild> </item1> <item1 id="a0" method="start"> <!-- this one is successive from the previous, because the previous node has id of 'a1', so we eliminate --> <somechild>a</somechild> </item1> <item1 id="a0" method="start"> <!-- this one is successive from the previous so we eliminate --> <somechild>a</somechild> </item1> </section> </node> </list></myroot>\[/code\]Expected Output:\[code\]<myroot> <list id="xxx"> <node id="a"> <section id="i"> <item1 id="a0" method="start"> <somechild>a</somechild> </item1> </section> <section id="i"> <item1 id="a1" method="start"> <somechild>a</somechild> </item1> </section> </node> </list></myroot>\[/code\]The idea is to remove successive node with the same method. In the example :
  • start/start/stop/start/start --> start/stop/start
The XSLT can remove successive node but not working for the scenario above.Can anyone point me to where should I change the xslt to accomodate above scenario? Really appreciate for the help.Cheers,John
 
Back
Top