2

xml を変換する xslt スタイル シートを作成しようとしています。私はミューエンチャン法を研究しましたが、それがどのように機能するかについてはよく知りません. すべての ManifestNo に任意の数の SequenceNo を含めることができるため、問題が発生しています。ソース xml のフラットな注文を、ネストされたストップの詳細を持つ宛先 xml の注文にグループ化しようとしています。

<Orders>
  <Order>
    <ManifestNo>283749</ManifestNo>
    <Warehouse>35</Warehouse>
    <SequenceNo>1</SequenceNo>
    <CustomerOrderNo>3524771-01</CustomerOrderNo>
    <Weight>180</Weight>
  </Order>
  <Order>
    <ManifestNo>283749</ManifestNo>
    <Warehouse>35</Warehouse>
    <SequenceNo>1</SequenceNo>
    <CustomerOrderNo>3524771-02</CustomerOrderNo>
    <Weight>250</Weight>
  </Order>
  <Order>
    <ManifestNo>283749</ManifestNo>
    <Warehouse>35</Warehouse>
    <SequenceNo>2</SequenceNo>
    <CustomerOrderNo>3524728-01</CustomerOrderNo>
    <Weight>25</Weight>
    </Order>
  <Order>
    <ManifestNo>283750</ManifestNo>
    <Warehouse>50</Warehouse>
    <SequenceNo>1</SequenceNo>
    <CustomerOrderNo>5464565-01</CustomerOrderNo>
    <Weight>150</Weight>
  </Order>
  <Order>
    <ManifestNo>283750</ManifestNo>
    <Warehouse>50</Warehouse>
    <SequenceNo>2</SequenceNo>
    <CustomerOrderNo>5874565-02</CustomerOrderNo>
    <Weight>125</Weight>
  </Order>
  <Order>
    <ManifestNo>283750</ManifestNo>
    <Warehouse>50</Warehouse>
    <SequenceNo>2</SequenceNo>
    <CustomerOrderNo>3524888-01</CustomerOrderNo>
    <Weight>95</Weight>
  </Order>
</Orders>

<Orders>
     <Order>
        <ManifestNo>283749</ManifestNo>
        <Warehouse>35</Warehouse> 
        <Stop>
            <SequenceNo>1</SequenceNo>
            <Freight>
                <CustomerOrderNo>3524771-01</CustomerOrderNo>
                <Weight>180</Weight>
            </Freight>
            <Freight>
                <CustomerOrderNo>3524771-02</CustomerOrderNo>
                <Weight>250</Weight>
            </Freight>
        </Stop>
        <Stop>
            <SequenceNo>2</SequenceNo>
            <Freight>
                <CustomerOrderNo>3524728-01</CustomerOrderNo>
                <Weight>25</Weight>
            </Freight>
            <Freight>
                <CustomerOrderNo>3524771-02</CustomerOrderNo>
                <Weight>250</Weight>
            </Freight>
        </Stop>
         </Order>
        <Order>
        <ManifestNo>283750</ManifestNo>
        <Warehouse>50</Warehouse> 
        <Stop>
            <SequenceNo>1</SequenceNo>
            <Freight>
                <CustomerOrderNo>5464565-01</CustomerOrderNo>
                <Weight>150</Weight>
            </Freight>
        </Stop>
        <Stop>
            <SequenceNo>2</SequenceNo>
            <Freight>
                <CustomerOrderNo>5874565-02</CustomerOrderNo>
                <Weight>125</Weight>
            </Freight>
            <Freight>
                <CustomerOrderNo>3524888-0</CustomerOrderNo>
                <Weight>95</Weight>
            </Freight>
        </Stop>
         </Order>
    </Orders>
4

1 に答える 1

1

I.このXSLT1.0変換

    <xsl:stylesheet version="1.0"
     xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
     <xsl:output omit-xml-declaration="yes" indent="yes"/>
     <xsl:strip-space elements="*"/>

     <xsl:key name="kOrderByNum" match="Order"
      use="ManifestNo"/>

     <xsl:key name="kSeqInOrder" match="SequenceNo"
      use="concat(../ManifestNo, '+', .)"/>

     <xsl:key name="kSeqByOrderNo" match="SequenceNo"
      use="../ManifestNo"/>

     <xsl:template match="Order"/>
     <xsl:template match="SequenceNo"/>

   <xsl:template match="/*">
     <Orders>
      <xsl:apply-templates/>
     </Orders>
     </xsl:template>

     <xsl:template match=
      "Order
         [generate-id()
         =
          generate-id(key('kOrderByNum', ManifestNo)[1])
          ]">
      <Order>
        <xsl:copy-of select="ManifestNo|Warehouse"/>

        <xsl:apply-templates select=
        "key('kSeqByOrderNo', ManifestNo)
          [generate-id()
          =
           generate-id(key('kSeqInOrder',
                           concat(../ManifestNo, '+', .)
                           )[1]
                      )
           ]
        "/>
      </Order>
     </xsl:template>

     <xsl:template match="SequenceNo[true()]">
      <Stop>
        <xsl:copy-of select="."/>
        <xsl:apply-templates mode="inGroup" select=
        "key('kSeqInOrder',
              concat(../ManifestNo, '+', .))"/>
      </Stop>
     </xsl:template>

     <xsl:template match="SequenceNo" mode="inGroup">
      <Freight>
        <xsl:copy-of select="../CustomerOrderNo|../Weight"/>
      </Freight>
     </xsl:template>
   </xsl:stylesheet>

提供されたXMLドキュメントに適用した場合:

<Orders>
  <Order>
    <ManifestNo>283749</ManifestNo>
    <Warehouse>35</Warehouse>
    <SequenceNo>1</SequenceNo>
    <CustomerOrderNo>3524771-01</CustomerOrderNo>
    <Weight>180</Weight>
  </Order>
  <Order>
    <ManifestNo>283749</ManifestNo>
    <Warehouse>35</Warehouse>
    <SequenceNo>1</SequenceNo>
    <CustomerOrderNo>3524771-02</CustomerOrderNo>
    <Weight>250</Weight>
  </Order>
  <Order>
    <ManifestNo>283749</ManifestNo>
    <Warehouse>35</Warehouse>
    <SequenceNo>2</SequenceNo>
    <CustomerOrderNo>3524728-01</CustomerOrderNo>
    <Weight>25</Weight>
    </Order>
  <Order>
    <ManifestNo>283750</ManifestNo>
    <Warehouse>50</Warehouse>
    <SequenceNo>1</SequenceNo>
    <CustomerOrderNo>5464565-01</CustomerOrderNo>
    <Weight>150</Weight>
  </Order>
  <Order>
    <ManifestNo>283750</ManifestNo>
    <Warehouse>50</Warehouse>
    <SequenceNo>2</SequenceNo>
    <CustomerOrderNo>5874565-02</CustomerOrderNo>
    <Weight>125</Weight>
  </Order>
  <Order>
    <ManifestNo>283750</ManifestNo>
    <Warehouse>50</Warehouse>
    <SequenceNo>2</SequenceNo>
    <CustomerOrderNo>3524888-01</CustomerOrderNo>
    <Weight>95</Weight>
  </Order>
</Orders>

必要な正しい結果を生成します。

<Orders>
   <Order>
      <ManifestNo>283749</ManifestNo>
      <Warehouse>35</Warehouse>
      <Stop>
         <SequenceNo>1</SequenceNo>
         <Freight>
            <CustomerOrderNo>3524771-01</CustomerOrderNo>
            <Weight>180</Weight>
         </Freight>
         <Freight>
            <CustomerOrderNo>3524771-02</CustomerOrderNo>
            <Weight>250</Weight>
         </Freight>
      </Stop>
      <Stop>
         <SequenceNo>2</SequenceNo>
         <Freight>
            <CustomerOrderNo>3524728-01</CustomerOrderNo>
            <Weight>25</Weight>
         </Freight>
      </Stop>
   </Order>
   <Order>
      <ManifestNo>283750</ManifestNo>
      <Warehouse>50</Warehouse>
      <Stop>
         <SequenceNo>1</SequenceNo>
         <Freight>
            <CustomerOrderNo>5464565-01</CustomerOrderNo>
            <Weight>150</Weight>
         </Freight>
      </Stop>
      <Stop>
         <SequenceNo>2</SequenceNo>
         <Freight>
            <CustomerOrderNo>5874565-02</CustomerOrderNo>
            <Weight>125</Weight>
         </Freight>
         <Freight>
            <CustomerOrderNo>3524888-01</CustomerOrderNo>
            <Weight>95</Weight>
         </Freight>
      </Stop>
   </Order>
</Orders>

II。XSLT 2.0ソリューション

<xsl:stylesheet version="2.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>

 <xsl:key name="kSeqByOrderNo" match="SequenceNo"
      use="../ManifestNo"/>

 <xsl:template match="/*">
   <Orders>
     <xsl:for-each-group select="Order" group-by="ManifestNo">
      <Order>
        <xsl:copy-of select="ManifestNo|Warehouse"/>

        <xsl:for-each-group select="key('kSeqByOrderNo', ManifestNo)"
         group-by=".">
         <xsl:copy-of select="."/>
         <Stop>
          <xsl:apply-templates select="current-group()"/>
         </Stop>
        </xsl:for-each-group>
      </Order>
     </xsl:for-each-group>
   </Orders>
 </xsl:template>

 <xsl:template match="SequenceNo">
   <Freight>
     <xsl:copy-of select="../CustomerOrderNo|../Weight"/>
   </Freight>
 </xsl:template>
</xsl:stylesheet>
于 2012-05-12T03:05:35.870 に答える