[xquery-talk] Selecting everything before and after path, but without duplicated leafs

Michael Kay mike at saxonica.com
Sun Feb 10 22:30:47 PST 2008


Three points:

(1) the preceding and following axes return each node once only. But if your
document is

<a>
  <b>
    <c/>
  </b>
  <d/>
</a>

then the preceding nodes of d are b and c, so if you do

<before>{//d/preceding::*}</before>

then the <before> element will contain a copy of b followed by a copy of c,
which means that the result will be

<before>
  <b>
    <c/>
  </b>
  <c/>
</before>

(2) You haven't really explained what output you want. If the input is

<ead>
  <banana/>
  <archdesc>
    <dsc>
      <c00/>
      <c01/>
      <c02/>
    </dsc>
  </archdesc>
  <custard/>
</ead>

what output would you like to see?

(3) Transformations that involve copying most of the source document to the
output unchanged while changing one or two nodes are generally easier to
code in XSLT. Unless you have external constraints on your choice of tools
(which isn't the case if you are using Saxon), then my advice is to use
XQuery for queries, XSLT for transformations.

Michael Kay
http://www.saxonica.com/

> -----Original Message-----
> From: talk-bounces at x-query.com 
> [mailto:talk-bounces at x-query.com] On Behalf Of Junte Zhang
> Sent: 10 February 2008 11:34
> To: talk at x-query.com
> Subject: [xquery-talk] Selecting everything before and after 
> path,but without duplicated leafs
> 
> Hi all,
> 
> I have an XML file (quite long) and I have a path to an 
> element. I want to select
> (1) everything of that path and its descendants, at the same 
> time I want to return everything (2) before that path, and 
> everything (3) after that path. I was trying the XPath axes 
> "preceding" and "following", but these axes are returning 
> duplicate leafs, which is not what I want. I would like to 
> reconstruct the original XML file, but with an extra tag for 
> the XPath selection ($unit).
> 
> This is how my XQuery looks like.
> 
>  let $doc := doc("file.xml")
> 
>  let $precedingUnit := 
> $doc/ead[1]/archdesc[1]/dsc[1]/c01[1]/preceding::node()
>  let $unit := $doc/ead[1]/archdesc[1]/dsc[1]/c01[1]/self::node()
>  let $followingUnit := 
> $doc/ead[1]/archdesc[1]/dsc[1]/c01[1]/following::node()
>  return
>  <out>
>   <before>
>   {
>      $precedingUnit
>   }
>   </before>
>   <select>
>   {
>      $unit
>   }
>   </select>
>   <after>
>   {
>      $followingUnit
>   }
>   </after>
>   </out>
> 
> I am using XQuery with Saxon: java -cp saxon9.jar 
> net.sf.saxon.Query query.xq
> 
> Could you please help me?
> 
> Thank you very much, I am really desperate in getting this working.
> 
> Kind regards
> 
> jz
> _______________________________________________
> talk at x-query.com
> http://x-query.com/mailman/listinfo/talk



More information about the talk mailing list