[XML-DEV Mailing List Archive Home] [By Thread] [By Date] [Recent Entries] [Reply To This Message] Parallel tree traversal
The discussion the other day on hierarchy and normalization got me thinking about a particular problem we have. I know this belongs on the XSLT list, but I'm being lazy and trying to avoid subscribing just to ask this one question (and I happen to know that some of the people who are likely to answer also hang out here... :-). We have a metadata structure that we use to manage our system in various ways. At some point we wish to build a hierarchical menu to traverse various specific data collections. The overall menu structure is reflected in the metadata similar to: <metadata> <a> <b> <c/> <d> <e> </d> </c> <f/> </a> </metadata> There are many attributes on each element giving various pieces of metadata, and in particular for this case, determining how a particular node gets presented in the menu. For a given metadata structure we need to map many possible data items, eg: <data> <a id="1"/> <b id="2" idref="1"/> <c id="3" idref="2/> <d id="4" idref="3"/> <e id="5" idref="4"/> <e id="6" idref="4"/> <c id="7" idref="2/> <f id="8" idref="1"/> <a id="9"/> <b id="10" idref="9"/> ... </data> Any given metadata node may not have any data associated with it. If it does, it must have a parent data item. Using the data structure I can determine that, in this, case I have to present a menu that has a structure like: <menu> <a id="1"> <b id="2"> <c id="3"/> <d id="4"> <e id="5"/> <e id="6"/> </d> </c> <c id="7"/> </b> <f id="8"/> </a> <a id="9"> <b id="10"> ... </a> </menu> The current strategy is to track the current id and pass it to a recursive XSLT template selecting all the data nodes that have an idref that is equal. It turns out that it would be easy to generate the tree structure for the data directly. However, I can't just use it directly, since if there is a missing data item I may still have to insert a menu item to create a new instance (depending on the metadata). So, I need to track the metadata as well. This is conceptually easy, just select the children of the current element and recursively pass it on to the template. However, practically, this is expensive in XSLT 1.0 since to subsequently use a parameter created in this manner it appears you have to use the nodeset function. Eg: <xsl:apply-templates select="*" mode="menu"> <xsl:with-param name="data" select="exslt:nodeset($data)/*"/> </xsl:apply-templates> Now, in this particular case we are using Saxon, so this raises two specific questions: 1) if I just declare the transform to be XSLT 1.1 and skip using the nodeset function will I see any performance gains? 2) Would using Saxon 7 and XSLT 2 have any performance gains? A more general question is whether anyone sees any other strategy for managing the above, or whether anyone has any opinions on which approach should work better? I can tell you that experiments with the second approach traversing the metadata and passing the data as a parameter seem to exhaust memory for large data trees though it works fine for smaller trees. I'm about to see if I can do the inverse from the above example: parse the data and pass the metadata as a parameter, but this is a non-trivial transform (lots of metadata affecting many things) so I thought I'd check first if anyone has a definite opinion about which way to proceed. Peter Hunsberger
|
PURCHASE STYLUS STUDIO ONLINE TODAY!Purchasing Stylus Studio from our online shop is Easy, Secure and Value Priced! Download The World's Best XML IDE!Accelerate XML development with our award-winning XML IDE - Download a free trial today! Subscribe in XML format
|