Subject: Re: [xsl] sequential navigation problem (long) From: Jakob.Fix@xxxxxxxxxxxxxxxxx Date: Thu, 5 Dec 2002 17:30:54 +0100 |
Jeni, David, Thanks for your responses. Thanks for pointing out the error in my logic. I am currently using the catch-all expressions, which works ok, (ancestor::* | preceding::*) [self::PART or self::CHAP or self::SECT or self::ART or self::SYMBOLS or self::APPENDIX or self::SART][@ID][last()] and (descendant::* | following::*) [self::PART or self::CHAP or self::SECT or self::ART or self::SYMBOLS or self::APPENDIX or self::SART][@ID][1] However, as you indicated, this slows down the processing enormously: normally, to fragment my 15 MB file into about 1800 fragments, it takes about 8 minutes. Currently, I am at 1040 fragments processed in 90 minutes ... another 800 to go ... An occasion to optimize ... I will also look into the function extension to modularize the stylesheet. Again, thanks for your quick replies! Jakob. Jeni Tennison <jeni@xxxxxxxxxxxxxxxx>@lists.mulberrytech.com on 12/05/2002 01:26:52 PM Veuillez répondre à xsl-list@xxxxxxxxxxxxxxxxxxxxxx Envoyé par : owner-xsl-list@xxxxxxxxxxxxxxxxxxxxxx Pour : Jakob Fix/HO/VERITAS@VERITAS cc : xsl-list@xxxxxxxxxxxxxxxxxxxxxx Objet : Re: [xsl] sequential navigation problem (long) Ref. Message: Hi Jakob, > In addition to the parent/next/prev sibling navigation, I want to add > sequential (in the book, page flicker sense) navigation as well, so that it > becomes possible to navigate the complete document only using "Next > fragment" or "Previous fragment" buttons. So, basically every fragment > must know the ID of the sequentially preceding and following fragment. > > For this I have defined the following algorithms: > > for previous fragment: > 1) test: node's left sibling has a last child with a known GI and an > ID > attr > 2) else test: node has a left sibling with a known GI and an ID attr > 3) else test: node has a parent with a known GI and an ID attr > > for next fragment: > 1) test: node has a first child with a known GI and an ID attr > 2) else test: node has sibling with a known GI and an ID attr > 3) else test: node's parent has a sibling with a known GI and an ID attr These tests miss out situations where, for example, you want the next fragment from a fragment whose parent doesn't have a following sibling but whose grandparent (or other ancestor) does. Rather than going through these separate tests, you might find it better to use the ancestor/descendant and preceding/following axes. For the previous fragment, you could use: (ancestor::* | preceding::*) [self::PART or self::CHAP or self::SECT or self::ART or self::SYMBOLS or self::APPENDIX or self::SART][@ID][last()] and for the next fragment, you could similarly use: (descendant::* | following::*) [self::PART or self::CHAP or self::SECT or self::ART or self::SYMBOLS or self::APPENDIX or self::SART][@ID][1] Using preceding and following will probably have an impact on the speed of the transformation, but you said you don't care too much about that -- try it and see. > where a "known GI" is one in this list (this is to avoid fragmenting > items such as notes and subsections which won't have their own > fragment, but have an ID nevertheless): "PART, CHAP, SECT, ART, > SYMBOLS, APPENDIX, SART" > > I have defined two named templates "tpl.next.fragment" and > "tpl.prev.fragment" which are called from the template responsible for > fragmenting, and are supposed to "return" the ID. Thus, the current node > is available in these templates. Please note, these templates are not yet > tested. > > My problem now is that I am not sure how to efficiently and > concisely write the XPath test expression of what is defined in the > algorithms. The following shows my approach, not tested. Your approach won't work, unfortunately, because you're holding the list of known GIs in a *string* and then trying to evaluate that string as part of an XPath expression. Actually, even if that did work, the expression that it would create wouldn't be a legal one... The easiest way to make your list of known.gis extensible with XSLT 1.0 is to store it in an entity: <!DOCTYPE xsl:stylesheet [ <!ENTITY known.gis 'self::PART or self::CHAP or self::SECT or self::ART or self::SYMBOLS or self::APPENDIX or self::SART'> ]> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> ... <xsl:template name="tpl.next.fragment"> <xsl:choose> <!-- does this node have a FIRST CHILD with an ID value and one of the GIs above? --> <xsl:when test="child::*[&known.gis;][@ID][1]"> </xsl:when> <!-- does this node have a FOLLOWING SIBLING with an ID value and one of the GIs above? --> <xsl:when test="following-sibling::*[&known.gis;][@ID][1]"> </xsl:when> <!-- does this node's PARENT DOES HAVE A NEXT SIBLING with an ID value and one of the GIs above? --> <xsl:when test="../following-sibling::*[&known.gis;][@ID]"> </xsl:when> <!-- not interested --> <xsl:otherwise/> </xsl:choose> </xsl:template> ... </xsl:stylesheet> If you're using a processor that supports func:function from EXSLT (e.g. Saxon or Xalan) and you're happy to use it, then I'd recommend writing a function that tests whether a given node is one of your known GIs or not, and then calling that function, as follows: <func:function name="my:is-known-GI"> <xsl:param name="n" /> <func:result select="$n/self::PART or $n/self::CHAP or $n/self::SECT or $n/self::ART or $n/self::SYMBOLS or $n/self::APPENDIX or $n/self::SART" /> </func:function> <xsl:template name="tpl.next.fragment"> <xsl:choose> <!-- does this node have a FIRST CHILD with an ID value and one of the GIs above? --> <xsl:when test="child::*[my:is-known-GI(.)][@ID][1]"> </xsl:when> <!-- does this node have a FOLLOWING SIBLING with an ID value and one of the GIs above? --> <xsl:when test="following-sibling::*[my:is-known-GI(.)][@ID][1]"> </xsl:when> <!-- does this node's PARENT DOES HAVE A NEXT SIBLING with an ID value and one of the GIs above? --> <xsl:when test="../following-sibling::*[my:is-known-GI(.)][@ID]"> </xsl:when> <!-- not interested --> <xsl:otherwise/> </xsl:choose> </xsl:template> I hope that gives you some ideas. Cheers, Jeni --- Jeni Tennison http://www.jenitennison.com/ XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list
Current Thread |
---|
|
<- Previous | Index | Next -> |
---|---|---|
Re: [xsl] sequential navigation pro, Joerg Heinicke | Thread | Re: [xsl] sequential navigation pro, David Carlisle |
Re: [xsl] qualitative decline of xs, Wendell Piez | Date | [xsl] A general <xsl:key> question., Edward L. Knoll |
Month |