[XSL-LIST Mailing List Archive Home] [By Thread] [By Date] [Recent Entries] [Reply To This Message]

Re: Multi-level grouping problem. MSXML bug, maybe?

Subject: Re: Multi-level grouping problem. MSXML bug, maybe?
From: Jeni Tennison <jeni@xxxxxxxxxxxxxxxx>
Date: Thu, 9 May 2002 10:10:02 +0100
name y key iden rss
Hi Mark,

> I want the output to look like:
>
> <?xml version="1.0" encoding="iso-8859-1"?>
> <CS>
>   <Co Type="F" SubType="S">
>     <DG Code="V" />
>     <DG Code="F" />
>   </Co>
>   <Co Type="F" SubType="T">
>     <DG Code="V" />
>   </Co>
> </CS>
>
> That is, I'm grouping by TYPE, SUB_TYPE, and D_CODE.

Yes, you've got two levels of grouping: one by TYPE and SUB_TYPE, and
one by D_CODE. Your key for grouping by TYPE and SUB_TYPE looks fine:

> <xsl:key name="row-by-type-subtype" match="row"
>          use="concat(TYPE/@value, '|', SUB_TYPE/@value)"/>

But your key for grouping by D_CODE is off. You have:

> <xsl:key name="d-by-type-subtype" match="D_CODE"
>          use="concat(../TYPE/@value, '|', ../SUB_TYPE/@value)"/>

This groups the D_CODE elements by their row's TYPE and SUB_TYPE; in
other words, it does exactly the same as the first key, except
grouping the D_CODE elements rather than the rows.

You want to group the *rows* by their D_CODE values. And because it's
the second level in the grouping, you need to incorporate the TYPE and
SUB_TYPE into that as well. So the key should look like:

<xsl:key name="row-by-d-code" match="row"
  use="concat(TYPE/@value, '|', SUB_TYPE/@value, '|', D_CODE/@value)"/>

Then you just do what you're doing, but use this key to filter the
rows with a particular TYPE and SUB_TYPE down to those with a unique
D_CODE as well:

  <xsl:for-each select="/recordset/row[count(. |
  key('row-by-type-subtype', concat(TYPE/@value, '|', SUB_TYPE/@value))[1]) = 1]">
    <xsl:variable name="type" select="TYPE/@value"/>
    <xsl:variable name="subtype" select="SUB_TYPE/@value"/>
    <xsl:variable name="type-subtype"
                  select="concat($type, '|', $subtype)" />
    <Co Type="{$type}" SubType="{$subtype}">
      <xsl:for-each select="key('row-by-type-subtype', $type-subtype)
        [count(.|key('row-by-d-code',
                     concat($type-subtype, '|', D_CODE/@value))[1])=1">
        <DG Code="{D_CODE/@value}" />
      </xsl:for-each>
    </Co>
  </xsl:for-each>

----

The XSLT 2.0 version:

  <xsl:for-each-group select="/recordset/row"
      group-by="concat(TYPE/@value, '|', SUB_TYPE/@value)">
    <Co Type="{TYPE/@value}" SubType="{SUB_TYPE/@value}">
      <xsl:for-each-group select="current-group()"
                          group-by="D_CODE/@value">
        <DG Code="{D_CODE/@value}" />
      </xsl:for-each-group>
    </Co>
  </xsl:for-each-group>
  
Cheers,

Jeni

---
Jeni Tennison
http://www.jenitennison.com/


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


Current Thread

PURCHASE STYLUS STUDIO ONLINE TODAY!

Purchasing Stylus Studio from our online shop is Easy, Secure and Value Priced!

Buy Stylus Studio Now

Download The World's Best XML IDE!

Accelerate XML development with our award-winning XML IDE - Download a free trial today!

Don't miss another message! Subscribe to this list today.
Email
First Name
Last Name
Company
Subscribe in XML format
RSS 2.0
Atom 0.3
Site Map | Privacy Policy | Terms of Use | Trademarks
Free Stylus Studio XML Training:
W3C Member
Stylus Studio® and DataDirect XQuery ™are products from DataDirect Technologies, is a registered trademark of Progress Software Corporation, in the U.S. and other countries. © 2004-2013 All Rights Reserved.