[XSL-LIST Mailing List Archive Home]
[By Thread]
[By Date]
[xsl] Collecting attributes from the ancestor-or-self axis
Subject: [xsl] Collecting attributes from the ancestor-or-self axis From: "B. Tommie Usdin" <btusdin@xxxxxxxxxxxxxxxx> Date: Fri, 16 Nov 2001 09:36:39 -0500 |
>From: "WATKIN-JONES,ADAM (HP-UnitedKingdom,ex1)" <adam_watkin-jones@xxxxxx> >To: "'xsl-list@xxxxxxxxxxxxxxxxxxxxxx'" <xsl-list@xxxxxxxxxxxxxxxxxxxxxx> >Subject: Help collecting attributes from the ancestor-or-self axis >Date: Fri, 16 Nov 2001 14:22:50 -0000 >Hello! > >I am trying to write some XSLT to do the following: > >1. start at element E >2. add all its attributes to the output >3. move to E's parent, EP >4. add to the output all those attributes > of EP that do not have the same name as > as an attribute already added to the output >5. move to EP's parent and so on collecting > new attributes until I've reached the last > ancestor of P. > >Below is some XML input, XML output and XSLT. >(Actually there's a second XSLT at the end as well.) > >The XSLT processes the input as intended but I'm not very satisfied with it >- it feels a bit cludgy and I'm concerned it will perform poorly on a big >input document. > >Question 1 > >The second XSLT represents an attempt to improve on the first. The problem >is that it requires a mysterious ingredient, possessed by very few (all >right then, maybe possessed by many but not by me!): ?something magical?. > >?something magical? is some XPath that takes a node set of attributes and an >element and it should find all the attributes of the element that do not >have the same name as an attribute in the node set. > >Question 2 >Have I got the basic technique wrong? Is there some more powerful magic out >there? (I tried to use the ancestor-or-self axis to construct a node set of >all attributes of interest and then turn it into some sort of grouping >problem but couldn't figure out how to make it work.) > > >Many thanks! > >Adam > > > >///////////////////////////////////////////////////////////////// >/// XML > ><?xml version="1.0"?> > ><elem1 > attr0="a" > attr1="b" > attr2="c" > attr3="d"> > <elem2 > attr1="e" > attr3="f" > attr4="g" > attr5="h" > attr6="i"> > <elem3 > attr1="j" > attr2="k" > attr7="l" > attr8="m" > attr9="n"/> > </elem2> ></elem1> > > >///////////////////////////////////////////////////////////////// >/// OUTPUT (Saxon 6.4.3) > ><?xml version="1.0" encoding="utf-8"?> ><attributes> > <attribute name="attr1" value="j" context="elem3"/> > <attribute name="attr2" value="k" context="elem3"/> > <attribute name="attr7" value="l" context="elem3"/> > <attribute name="attr8" value="m" context="elem3"/> > <attribute name="attr9" value="n" context="elem3"/> > <attribute name="attr3" value="f" context="elem2"/> > <attribute name="attr4" value="g" context="elem2"/> > <attribute name="attr5" value="h" context="elem2"/> > <attribute name="attr6" value="i" context="elem2"/> > <attribute name="attr0" value="a" context="elem1"/> ></attributes> > > >///////////////////////////////////////////////////////////////// >/// XSLT > ><?xml version="1.0" encoding="UTF-8"?> > ><xsl:stylesheet > version="1.0" > xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> > > <xsl:output method="xml" indent="yes"/> > > > <xsl:template match="/"> > <attributes> > <xsl:call-template name="GetAttributes"> > <xsl:with-param name="nsAttributes" select="/.."/> > <xsl:with-param name="nsContext" >select="elem1/elem2/elem3"/> > </xsl:call-template> > </attributes> > </xsl:template> > > > <xsl:template name="GetAttributes"> > > <xsl:param name="nsAttributes"/> > <xsl:param name="nsContext"/> > > <xsl:variable name="nsNewAttributes"> > <dummy> > <xsl:for-each select="$nsContext/attribute::*"> > <xsl:if test="count($nsAttributes/dummy/attribute/ > @name[. = name(current())]) = 0"> > <attribute name="{name()}"/> > </xsl:if> > </xsl:for-each> > </dummy> > </xsl:variable> > > <xsl:variable name="nsParent" select="$nsContext/.."/> > > <xsl:for-each select="$nsContext/attribute::*"> > <xsl:if test="0 = count($nsAttributes/dummy/attribute/ > @name[. = name(current())])"> > <attribute name="{name()}" value="{.}" > context="{name($nsContext)}"/> > </xsl:if> > </xsl:for-each> > > <xsl:if test="$nsParent"> > <xsl:call-template name="GetAttributes"> > <xsl:with-param name="nsAttributes" > select="$nsAttributes | $nsNewAttributes"/> > <xsl:with-param name="nsContext" select="$nsParent"/> > </xsl:call-template> > </xsl:if> > > </xsl:template> > > ></xsl:stylesheet> > > >///////////////////////////////////////////////////////////////// >/// XSLT Preferred (just requires ?something magical?) > ><?xml version="1.0" encoding="UTF-8"?> > ><xsl:stylesheet > version="1.0" > xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> > > <xsl:output method="xml" indent="yes"/> > > > <xsl:template match="/"> > <attributes> > <xsl:call-template name="GetAttributes"> > <xsl:with-param name="nsAttributes" select="/.."/> > <xsl:with-param name="nsContext" >select="elem1/elem2/elem3"/> > </xsl:call-template> > </attributes> > </xsl:template> > > > <xsl:template name="GetAttributes"> > > <xsl:param name="nsAttributes"/> > <xsl:param name="nsContext"/> > > <xsl:variable name="nsNewAttributes" select="?something magical?"> > > <xsl:variable name="nsParent" select="$nsContext/.."/> > > <xsl:for-each select="$nsNewAttributes"> > <attribute name="{name()}" value="{.}" > context="{name($nsContext)}"/> > </xsl:for-each> > > <xsl:if test="$nsParent"> > <xsl:call-template name="GetAttributes"> > <xsl:with-param name="nsAttributes" > select="$nsAttributes | $nsNewAttributes"/> > <xsl:with-param name="nsContext" select="$nsParent"/> > </xsl:call-template> > </xsl:if> > > </xsl:template> > > ></xsl:stylesheet> XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list
Current Thread |
---|
|
<- Previous | Index | Next -> |
---|---|---|
Re: [xsl] A riddle..., David Carlisle | Thread | Re: [xsl] Collecting attributes fro, David Carlisle |
Re: [xsl] Re: Re: Re: Re: order of , Jeni Tennison | Date | RE: [xsl] xml 2 csv, Jan Weiss |
Month |