RE: [xsl] Re: select distinct

Subject: RE: [xsl] Re: select distinct
From: "Passin,Thomas B. (Tom)" <tpassin@xxxxxxxxxxxx>
Date: Tue, 17 Sep 2002 11:45:21 -0400
[ Noel Golding]
> 
> Thanks for the link, however it stills seems a little over my 
> head. How to get all the unique <ref/> elements?
> 
> I assume my xsl:key element would look like
> 
> <xsl:key name="name-of-unique-list" match="ref" use="@name" />
> 
> but then how do I make sure I am matching on all ref elements 
> regardless of where they are located in the document?
> 

That is how keys work.  This key will index all the "ref" elements.  The
key itself will not give you a unique list, but the Munchean method
together with the key will.  

There are different ways to apply the Munchean approach - you can create
a variable containing all the unique nodes, or you can create a result
tree fragment for output, as in Dimitre's example that you looked at.
Here is a pretty standard way - it shows up in various FAQ pages and in
Mike Kay's book "XSLT Programmer's Reference 2nd Edition" - to get a
nodeset containing unique "ref" (that is, they have unique "name"
attribute values)  elements:

<xsl:key name='refs' match='ref' use='@name'/>
<xsl:variable name='unique-refs'
   select='//ref[generate-id(.)=generate-id(key("refs",@name)[1])]'/>

This works as follows - the nodeset of the variable contains only those
"ref" nodes that the key returns, and of those, only the first of each
series returned by the key.  Thus, for each value of the "name"
attribute, you get exactly the first "ref" node whose "name" attribute
contains that value.  Therefore the nodeset contains no duplicates. 

The count(. | xxx) technique you looked at can be made to work as well,
and one or the other may be more convenient depending on just what you
want to accomplish.

Now, this variable will contain "ref" elements wherever they may be in
the document.  If, in your example, you only wanted to look at 'ref'
elements that are unique within all /document/section/para elements, you
would change the variable to

<xsl:variable name='unique-para-refs'
 
select='/document/section/para/ref[generate-id(.)=generate-id(key("refs"
,@name)[1])]'/>

Cheers,

Tom P

 XSL-List info and archive:  http://www.mulberrytech.com/xsl/xsl-list


Current Thread