[xsl] [Fwd: Muenchian method -- how to optimize this code ?]

Subject: [xsl] [Fwd: Muenchian method -- how to optimize this code ?]
From: Michael Fourneau <Michael.Fourneau@xxxxxxx>
Date: Fri, 18 Aug 2006 10:27:18 +0200
Hi,

Could anyone please confirm that this email has ever reached the mailing list ? It was sent as a plain-text and without attachement...

Thanks,
Michael

-------- Original Message --------

=== Posted to xsl-list@xxxxxxxxxxxxxxxxxxxxxx on Wed Aug 16 23:50:48 2006 CEST ===


(It seems that my previous emails did not reach this list, hope this works now...)



Hi Gurus,


Seems that I found the way to create the name_title key which holds the expected data.

I've also created the stylesheet which creates my HTML file in a unique table. But I'm not sure at all, I've created it in the most efficient way. With this very small example, it takes already 1.6 secondes to transform it with XMLStarlet on an hold Solaris 9 SPARC system with 400 Mhz CPU's. The problem is that the whole XML file is parsed for each name_title association. With the real XML file, it takes some 13 secondes to transform the XML file for only 100 customers.

I'd like now to optimize the stylesheet to create a specific table (with two headers: Team member and Customers) for each TITLE found in the document (4 titles in the example). What would be the best way to do it ?

You'll find hereunder: * The example XML document ; * The stylesheet ; * and the result HTML file.



====> This XML document:


<?xml version="1.0" encoding="iso-8859-1" ?>


<customers> <customer> <name>CUSTOMER1</name> <team> <member> <name>NAME1</name> <title>T1</title> <title>T2</title> </member> <member> <name>NAME2</name> <title>T3</title> </member> </team> </customer> <customer> <name>CUSTOMER2</name> <team> <member> <name>NAME3</name> <title>T4</title> </member> <member> <name>NAME2</name> <title>T3</title> <title>T1</title> </member> </team> </customer> <customer> <name>CUSTOMER3</name> .... </customer> </customers>





====> With the following stylesheet:


<?xml version="1.0" encoding="ISO-8859-1"?>


<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform";>

<xsl:key name="title" match="/customers/customer/team/member/title" use="."/> <xsl:key name="name_title" match="/customers/customer/team/member/title" use="concat(../name,',',.)" />

<!-- MAIN template -->

<xsl:template match="/"> <html> <head> <title>Managed Accounts -- Customers assigned by title</title>

</head> <body>


<h2>Managed Accounts -- Customers assigned by title -- FOR TESTS PURPOSE ONLY</h2>


<h3>Unique titles</h3> <ul> <xsl:for-each select="customers/customer/team/member/title[generate-id(.)=generate-id(key('title',.))]"> <xsl:sort select="title"/> <li><xsl:value-of select="."/></li> </xsl:for-each> </ul>


<h3>Account assignements</h3>


<table class="ltgrey"> <tr> <th class="dkblue">Title</th> <th class="dkblue">Team member</th> <th class="dkblue">Customers</th> </tr>

<xsl:for-each select="customers/customer/team/member/title[generate-id(.)=generate-id(key('name_title',concat(../name,',',.)))]"> <xsl:sort select="."/> <xsl:sort select="../name"/> <xsl:variable name="this" select="concat(../name,',',.)"></xsl:variable> <tr> <td class="vatop"><xsl:value-of select="."/></td> <td class="vatop"><xsl:value-of select="../name"/></td> <td class="vatop"> <ol> <xsl:for-each select="/customers/customer/team/member/title[concat(../name,',',.)=$this]"> <xsl:sort select="../../../name"/> <li> <xsl:value-of select="../../../name"/> [<xsl:value-of select="../../../countrycode"/>] </li> </xsl:for-each> </ol> </td>

</tr> </xsl:for-each> </table>

</body> </html> </xsl:template> </xsl:stylesheet>




====> Gives:



<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> <title>Managed Accounts -- Customers assigned by title</title> </head> <body> <h2>Managed Accounts -- Customers assigned by title -- FOR TESTS PURPOSE ONLY</h2> <h3>Unique titles</h3> <ul> <li>T1</li> <li>T2</li> <li>T3</li>


<li>T4</li> </ul> <h3>Account assignements</h3> <table class="ltgrey"> <tr> <th class="dkblue">Title</th> <th class="dkblue">Team member</th> <th class="dkblue">Customers</th> </tr> <tr> <td class="vatop">T1</td>

<td class="vatop">NAME1</td> <td class="vatop"><ol><li>CUSTOMER1 [] </li></ol></td> </tr> <tr> <td class="vatop">T1</td> <td class="vatop">NAME2</td> <td class="vatop"><ol><li>CUSTOMER2 [] </li></ol></td> </tr> <tr> <td class="vatop">T2</td> <td class="vatop">NAME1</td>

<td class="vatop"><ol><li>CUSTOMER1 [] </li></ol></td> </tr> <tr> <td class="vatop">T3</td> <td class="vatop">NAME2</td> <td class="vatop"><ol> <li>CUSTOMER1 [] </li> <li>CUSTOMER2 [] </li> </ol></td> </tr> <tr> <td class="vatop">T4</td>

<td class="vatop">NAME3</td> <td class="vatop"><ol><li>CUSTOMER2 [] </li></ol></td> </tr> </table> </body> </html>




====> Initial request:



Hi,


I'm just beginning with XML and XSLT, I've used the "Jeni's XSLT pages: grouping using the Muenchian Method" @ http://www.jenitennison.com/xslt/grouping/index.xml to start my first steps. Thus, I have created an XML document in which any customer has a team composed of several members, who can have several "titles" associated to a unique name in the team. The structure of the XML document looks like this:

<customers> <customer> <name>CUSTOMER1</name> <team> <member> <name>NAME1</name> <title>T1</title> <title>T2</title> </member> <member> <name>NAME2</name> <title>T3</title> </member> </team> </customer> <customer> <name>CUSTOMER2</name> <team> <member> <name>NAME3</name> <title>T4</title> </member> <member> <name>NAME2</name> <title>T3</title> <title>T1</title> </member> </team> </customer> <customer> <name>CUSTOMER3</name> .... </customer> </customers>



In the stylesheet, I defined the key "name_title" which is supposed to contain all the associations of name and title(s) found in the XML document. And actually, it works fine for the first occurence of the <title> element, but any further <title> elements (for the same member) are just added to the first one...

<xsl:key name="name_title" match="/customers/customer/team/member" use="concat(name,' ',following-sibling::member/title)" />


With the key I've written, the "name_title" table contain:


NAME1 T1 T2 NAME2 T3 NAME3 T4 NAME2 T3 T1

although I'm expecting :

NAME1 T1 NAME1 T2 NAME2 T3 NAME3 T4 NAME2 T3 NAME2 T1


=== Question 1 ===


* How can I solve this "small" issue ?

=== Question 2 ===

* From this XML document, I'd like to created a table which contains: o in the first column: the titles found in the document ; o in the second column: the name of the members with such title ; o in the third column: all the customers which have this member - with this title - in their team. * How could I achieve this based on the Muenchian method ?

The result table should look like:

T1 NAME1 CUSTOMER1

NAME2 CUSTOMER2

T2 NAME1 CUSTOMER1

T3 NAME2 CUSTOMER1 CUSTOMER2

T4 NAME3 CUSTOMER2


Thanks beforehand, Michael Fourneau

Current Thread