Re: [xsl] XML/XSLT Problem

Subject: Re: [xsl] XML/XSLT Problem
From: Joerg Heinicke <joerg.heinicke@xxxxxx>
Date: Wed, 31 Jul 2002 04:37:43 +0200
Hi Alex,

test if this stylesheet meets your expectations:

<xsl:template match="abc">
    <xsl:copy>
        <xsl:apply-templates select="PP"/>
    </xsl:copy>
</xsl:template>

<xsl:template match="PP">
    <Group>
        <xsl:copy-of select="."/>
        <xsl:apply-templates select="../IP[@id = current()/IPI/@id]"/>
    </Group>
</xsl:template>

<xsl:template match="IP">
    <xsl:copy-of select="."/>
    <xsl:apply-templates select="../PR[@id = current()/@id-1]"/>
</xsl:template>

<xsl:template match="PR">
    <xsl:copy-of select="."/>
</xsl:template>


XML input


<abc>
    <PP id="111" id-1="222" >
      <IPI id="333" id-2="444" >
       <p1>p1p1p1</p1>
      </IPI>
      <IPI id="sss" id-2="666" >
       <p1>p2p2p2</p1>
      </IPI>
    </PP>
    <PP id="777" id-1="888" >
      <IPI id="123" id-2="234" >
       <p1>p3p3p3</p1>
      </IPI>
      <IPI id="456" id-2="567" >
       <p1>p4p4p4</p1>
      </IPI>
    </PP>
    <IP id="rrr" id-1="aaa">
      <i1>i1i1i1</i1>
    </IP>
    <IP id="sss" id-1="bbb">
      <i1>i2i2i2</i1>
    </IP>
    <IP id="ttt" id-1="ccc">
      <i1>i3i3i3</i1>
    </IP>
    <IP id="uuu" id-1="ddd">
      <i1>i4i4i4</i1>
    </IP>
    <PR id="xxx">
      <r1>r1r1r1</r1>
    </PR>
    <PR id="bbb">
      <r1>r2r2r2</r1>
    </PR>
    <PR id="zzz">
      <r1>r3r3r3</r1>
    </PR>
</abc>


XML output


<abc>
    <Group>
        <PP id="111" id-1="222">
            <IPI id="333" id-2="444">
                <p1>p1p1p1</p1>
            </IPI>
            <IPI id="sss" id-2="666">
                <p1>p2p2p2</p1>
            </IPI>
        </PP>
        <IP id="sss" id-1="bbb">
            <i1>i2i2i2</i1>
        </IP>
        <PR id="bbb">
            <r1>r2r2r2</r1>
        </PR>
    </Group>
    <Group>
        <PP id="777" id-1="888">
            <IPI id="123" id-2="234">
                <p1>p3p3p3</p1>
            </IPI>
            <IPI id="456" id-2="567">
                <p1>p4p4p4</p1>
            </IPI>
        </PP>
    </Group>
</abc>

If the file is much bigger and you have to compare many elements by their @id's, it's better to setup keys and use them for faster element access.

Regards,

Joerg


Alex Genis wrote:
Hi, G.Ken.
Thanks a lot for your help. Your XSLT works perfectly.
But this is not exactly what I was looking for (maybe because I've
described my task not clear enough).

1. What if an input XML Document contains a few groups (each of which
contains  "PP", "IP" and "PR" elements
    connected between each other by the same condition: (PP/IPI/@id =
IP/@id) and (IP/@id-1 = PR/@id))?
    When I tested your Stylesheet I've created such input XML Document and
result XML looked like :
    <abc>
       <PP id="..." id-1="...">
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
       </PP>
       <PP id="..." id-1="...">
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
       </PP>
       <IP id="..." id-1="...">
          <i1>...</i1>
       </IP>
       <IP id="..." id-1="...">
          <i1>...</i1>
       </IP>
       <PR id="...">
          <r1>...</r1>
       </PR>
       <PR id="...">
          <r1>...</r1>
       </PR>
   </abc>

My question is: how can I combine them like:

<abc>
    <Group>
        <PP id="..." id-1="...">
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
        </PP>
        <IP id="..." id-1="...">
              <i1>...</i1>
        </IP>
        <PR id="...">
             <r1>...</r1>
       </PR>
    </Group>
    <Group>
        <PP id="..." id-1="...">
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
           <IPI id="..." id-2="...">
                <p1>....</p1>
           </IPI>
        </PP>
        <IP id="..." id-1="...">
              <i1>...</i1>
        </IP>
        <PR id="...">
             <r1>...</r1>
       </PR>
     </Group>
  </abc>

  where each group contains only elements connected between each other by
condition (above).

Because my task is :
    To create for each such group set of output elements.
    Each of this output element must contain children value of which should
be generated
         from an some attributes and elements of the appropriate group.

Therefore I want those sets of "PP", "IP", and "PR" to be grouped -
just to have a possibility reading this XML to use <xsl:for-each select
="Group">.....</xsl:for-each>.

2. And by the way does it mean that the task (above) must contain two
steps:
    a) XSLT-1  which creates  XML containing those groups;
    b) XSLT-2  which reads this XML and create output elements for each
group.
   Or it's possible to perform this in one shot ?

Thank you very much for your help again.


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


Current Thread