Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > XML > Use apply-templates selectively in XSLT

Reply
Thread Tools

Use apply-templates selectively in XSLT

 
 
abhishek.smu@gmail.com
Guest
Posts: n/a
 
      02-23-2007
Given an XML like:

<root>
<node>8</node>
<node>21</node>
<node>-7</node>
<node>13</node>
<node>43</node>
<node>2</node>
</root>


how might I select only the 2nd, 3rd and 4th nodes (or more
generically, any selective set of nodes like first 4, last 3, every
other node etc)? Note that since my XSLT obviously won't know the
value inside a node, I can't just pick a node with the values of 21,
-7 and 13 using xsl:if or something like it. I tried playing around
with some things like for-each and creating a template with some sort
of a recursive scenario, but to no avail.


Any help is appreciated.


Thanks


Abhishek

 
Reply With Quote
 
 
 
 
Joseph Kesselman
Guest
Posts: n/a
 
      02-23-2007
wrote:
> how might I select only the 2nd, 3rd and 4th nodes


Write a select expression that tests position().

--
Joe Kesselman / Beware the fury of a patient man. -- John Dryden
 
Reply With Quote
 
 
 
 
roy axenov
Guest
Posts: n/a
 
      02-23-2007
On Feb 23, 7:51 pm, "abhishek....@gmail.com"
<abhishek....@gmail.com> wrote:
> <root>
> <node>8</node>
> <node>21</node>
> <node>-7</node>
> <node>13</node>
> <node>43</node>
> <node>2</node>
> </root>
>
> how might I select only the 2nd, 3rd and 4th nodes


<xsl:template match="node"/>
<xsl:template
match="node[position() &gt; 1 and position() &lt; 5]">
<xsl:copy><xsl:apply-templates/></xsl:copy>
</xsl:template>

> (or more generically, any selective set of nodes like
> first 4,


<xsl:template match="node"/>
<xsl:template
match="node[count(preceding-sibling::node) &lt; 4]">
<xsl:copy><xsl:apply-templates/></xsl:copy>
</xsl:template>

> last 3,


<xsl:template match="node"/>
<xsl:template
match="node[count(following-sibling::node) &lt; 3]">
<xsl:copy><xsl:apply-templates/></xsl:copy>
</xsl:template>

> every other node


<xsl:template match="node"/>
<xsl:template
match="node[position() mod 2=0]">
<xsl:copy><xsl:apply-templates/></xsl:copy>
</xsl:template>

Note that depending on what exactly you are trying to do,
it might be a good idea to use xsl:key/key() combo together
with selecting the nodesets you need instead of
template-based matching of the nodes you need processed.

> Note that since my XSLT obviously won't know the value
> inside a node


I beg your pardon? Of course it will. Use string() or just
'.'. Note that this is a bit esoteric and often not a very
good practice if you stop and think about it for a moment.
Anyway, processing based on a value of the node is
definitely possible.

> I can't just pick a node with the values of 21, -7 and 13


Of course you can.

<xsl:template match="node"/>
<xsl:template
match="node[.=21 or .=-7 or .=13]">
<xsl:copy><xsl:apply-templates/></xsl:copy>
</xsl:template>

Or did you mean that your problem requires matching of
nodes based on their position in the document, not on the
plain data they contain? If that is the case, the solutions
are described above.

Another thing to keep in mind is that if you're processing
a homogeneous nodeset using node position to switch
processing modes, it is often an indicator of poor XML
design of your source document; but whatever suits you.

> using xsl:if or something like it. I tried playing around
> with some things like for-each


As a rule of the thumb, if and choose should be replaced
with predicate-based selection and matching where possible.
Where impossible, go ahead and use if or choose, but
remember that it's a good idea to feel somewhat dirty and
uncomfortable afterwards.

You should also realize that for-each is very different
from what you would expect out of similarly based language
constructs or library methods in imperative languages such
as Perl, PHP, C++ or Java. Use template-based processing
instead.

> and creating a template with some sort of a recursive
> scenario, but to no avail.


I'm not sure I can see how recursive processing would be
helpful in this particular case.

--
roy axenov

 
Reply With Quote
 
abhishek.smu@gmail.com
Guest
Posts: n/a
 
      02-24-2007
On Feb 23, 2:03 pm, "roy axenov" <r_axe...@mail.ru> wrote:
> On Feb 23, 7:51 pm, "abhishek....@gmail.com"
>
> <abhishek....@gmail.com> wrote:
> > <root>
> > <node>8</node>
> > <node>21</node>
> > <node>-7</node>
> > <node>13</node>
> > <node>43</node>
> > <node>2</node>
> > </root>

>
> > how might I select only the 2nd, 3rd and 4th nodes

>
> <xsl:template match="node"/>
> <xsl:template
> match="node[position() &gt; 1 and position() &lt; 5]">
> <xsl:copy><xsl:apply-templates/></xsl:copy>
> </xsl:template>
>
> > (or more generically, any selective set of nodes like
> > first 4,

>
> <xsl:template match="node"/>
> <xsl:template
> match="node[count(preceding-sibling::node) &lt; 4]">
> <xsl:copy><xsl:apply-templates/></xsl:copy>
> </xsl:template>
>
> > last 3,

>
> <xsl:template match="node"/>
> <xsl:template
> match="node[count(following-sibling::node) &lt; 3]">
> <xsl:copy><xsl:apply-templates/></xsl:copy>
> </xsl:template>
>
> > every other node

>
> <xsl:template match="node"/>
> <xsl:template
> match="node[position() mod 2=0]">
> <xsl:copy><xsl:apply-templates/></xsl:copy>
> </xsl:template>
>
> Note that depending on what exactly you are trying to do,
> it might be a good idea to use xsl:key/key() combo together
> with selecting the nodesets you need instead of
> template-based matching of the nodes you need processed.
>
> > Note that since my XSLT obviously won't know the value
> > inside a node

>
> I beg your pardon? Of course it will. Use string() or just
> '.'. Note that this is a bit esoteric and often not a very
> good practice if you stop and think about it for a moment.
> Anyway, processing based on a value of the node is
> definitely possible.
>
> > I can't just pick a node with the values of 21, -7 and 13

>
> Of course you can.
>
> <xsl:template match="node"/>
> <xsl:template
> match="node[.=21 or .=-7 or .=13]">
> <xsl:copy><xsl:apply-templates/></xsl:copy>
> </xsl:template>
>
> Or did you mean that your problem requires matching of
> nodes based on their position in the document, not on the
> plain data they contain? If that is the case, the solutions
> are described above.
>
> Another thing to keep in mind is that if you're processing
> a homogeneous nodeset using node position to switch
> processing modes, it is often an indicator of poor XML
> design of your source document; but whatever suits you.
>
> > using xsl:if or something like it. I tried playing around
> > with some things like for-each

>
> As a rule of the thumb, if and choose should be replaced
> with predicate-based selection and matching where possible.
> Where impossible, go ahead and use if or choose, but
> remember that it's a good idea to feel somewhat dirty and
> uncomfortable afterwards.
>
> You should also realize that for-each is very different
> from what you would expect out of similarly based language
> constructs or library methods in imperative languages such
> as Perl, PHP, C++ or Java. Use template-based processing
> instead.
>
> > and creating a template with some sort of a recursive
> > scenario, but to no avail.

>
> I'm not sure I can see how recursive processing would be
> helpful in this particular case.
>
> --
> roy axenov


WOW !!!

Thank you so much. Since I am a beginner at this, I had never even
heard of the node and position things. This is absolute magic to me.

And yes, I did mean that my "problem requires matching of nodes based
on their position in the document, not on the plain data they
contain."

Once again, thanks a lot.

Abhishek

 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
How to selectively hide Wireless Network Connection icon =?Utf-8?B?SmFtZXM=?= Wireless Networking 1 10-27-2005 10:18 PM
Selectively removing Cache Key tarunbajaj@gmail.com ASP .Net 4 08-09-2005 08:19 PM
Use router to selectively block file sharing on one of my computers? Roger Wireless Networking 2 02-17-2005 01:01 AM
receive selectively from a DatagramSocket Lorenzo Bettini Java 4 02-16-2005 08:01 AM
Thunderbird-Remote images selectively not showing Jim Blue Firefox 11 04-15-2004 08:56 AM



Advertisments
 



1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57