2014-12-04 133 views
0

我在組合多個密鑰以獲取更改的記錄時遇到問題。組合多個密鑰

我有2條XML記錄。文件1和文件2

目標是創建一個包含4個部分的表格。相同,更改,添加和刪除。

在兩個文檔中都有相同的rec_no,part_no,ext_qty的元素應該進入子部分Same。 在Document1中存在但不在Document2中的元素需要在Delete子部分下 在Document2中存在且不在Document1中的元素需要在Add部分下 在上述3個條件中不存在的元素應該在更改子部分中。例如, 這兩個文件中都有記錄,並且數量或零件編號或描述中有任何更改

現在我可以添加前3個部分而沒有任何問題,問題出現在第4個條件中。我無法將前三項條件組合起來得到這些條件的「不」。

這裏是我的評論輸出表。這裏記錄999有在刪除部分,它不應該在改款

---------------------------------------------------- 
Section PartNo RecNo Desc Doc-1 Qty Doc-2 Qty Total 
---------------------------------------------------- 
Same 111  aaa Desc1 1   1  200 
---------------------------------------------------- 
Same Total         100 
---------------------------------------------------- 
Change 222  bbb Desc2 2   3  200 
Change 333  ccc Desc3 3   3  200 
Change 444  ddd Desc4 6   4  500 
Change 999  ggg Desc9 2   0  100 
---------------------------------------------------- 
Change Total         400 
---------------------------------------------------- 
Add  666  ff Desc4 0   6  400 
---------------------------------------------------- 
Add Total          0 
---------------------------------------------------- 
Delete 999  ggg Desc9 2   0  100 
---------------------------------------------------- 
Delete Total         0 
---------------------------------------------------- 
Grand Total         500 
---------------------------------------------------- 

來到這裏是我的XML

<?xml version="1.0" encoding="utf-8"?> 
<?xml-stylesheet type="text/xsl" href="sample.xslt"?> 
<Logia> 
    <DocHeader> 
    <Document> 
     <Downto> 
     <part_no>111</part_no> 
     <rec_no>aaa</rec_no> 
     <desc>Desc1</desc> 
     <ext_qty>1</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>222</part_no> 
     <rec_no>bbb</rec_no> 
     <desc>Desc2</desc> 
     <ext_qty>2</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>333</part_no> 
     <rec_no>ccc</rec_no> 
     <desc>Desc3</desc> 
     <ext_qty>3</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>444</part_no> 
     <rec_no>ddd</rec_no> 
     <desc>Desc4</desc> 
     <ext_qty>6</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>999</part_no> 
     <rec_no>ggg</rec_no> 
     <desc>Desc9</desc> 
     <ext_qty>2</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
    </Document> 
    <Document> 
     <Downto> 
     <part_no>111</part_no> 
     <rec_no>aaa</rec_no> 
     <desc>Desc1</desc> 
     <ext_qty>1</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>222</part_no> 
     <rec_no>bbb</rec_no> 
     <desc>Desc3</desc> 
     <ext_qty>3</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>333</part_no> 
     <rec_no>bbb</rec_no> 
     <desc>Desc3</desc> 
     <ext_qty>3</ext_qty> 
     <mat_cost>100.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>444</part_no> 
     <rec_no>ddd</rec_no> 
     <desc>Desc4</desc> 
     <ext_qty>4</ext_qty> 
     <mat_cost>400.00</mat_cost> 
     </Downto> 
     <Downto> 
     <part_no>666</part_no> 
     <rec_no>ff</rec_no> 
     <desc>Desc4</desc> 
     <ext_qty>6</ext_qty> 
     <mat_cost>400.00</mat_cost> 
     </Downto> 
    </Document> 
    </DocHeader> 
</Logia> 

和我的XSL是如下

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

<xsl:key name="MAT1PARTKEY" match="Document[1]/Downto" use="part_no" /> 
<xsl:key name="MAT2PARTKEY" match="Document[2]/Downto" use="part_no" /> 

<xsl:key name="MATERIALBYPARTNO" match="Document/Downto" use="part_no" /> 

<xsl:key name="MATERIAL2BYKEY" match="Document[2]/Downto" use="concat(rec_no, '||', part_no, '||', ext_qty)" /> 
    <xsl:key name="MATERIALKEY" match="Document[1]/Downto" use="concat(rec_no, '||', part_no, '||', ext_qty)" /> 

<xsl:template match="/Logia/DocHeader"> 
    <table border="1"> 
     <!-- header --> 
     <tr> 
      <th>Section</th> 
      <th>PartNo</th> 
      <th>RecNo</th> 
      <th>Desc</th> 
      <th>Doc-1 Qty</th> 
      <th>Doc-2 Qty</th> 
      <th>Total</th> 
     </tr> 
     <!-- same --> 
     <xsl:variable name="same" select="Document[1]/Downto[key('MATERIAL2BYKEY', concat(rec_no, '||', part_no, '||', ext_qty))]" /> 
     <xsl:apply-templates select="$same"> 
      <xsl:with-param name="section">Same</xsl:with-param> 
     </xsl:apply-templates> 
     <xsl:variable name="same-total" select="sum($same/mat_cost)" />  
     <tr> 
      <td colspan="6">Same Total</td> 
      <th><xsl:value-of select="$same-total"/></th> 
     </tr>  
     <!-- change --> 
     <xsl:variable name="change" select="Document[1]/Downto[not(key('MATERIAL2BYKEY', concat(rec_no, '||', part_no, '||', ext_qty)))]" /> 
     <xsl:apply-templates select="$change"> 
      <xsl:with-param name="section">Change</xsl:with-param> 
     </xsl:apply-templates> 
     <xsl:variable name="change-total" select="sum($change/mat_cost)" />  
     <tr> 
      <td colspan="6">Change Total</td> 
      <th><xsl:value-of select="$change-total"/></th> 
     </tr>     
     <!-- Add --> 
     <xsl:variable name="add" select="Document[2]/Downto[not(key('MAT1PARTKEY', part_no))]" /> 
     <xsl:apply-templates select="$add"> 
      <xsl:with-param name="section">Add</xsl:with-param> 
     </xsl:apply-templates> 
     <xsl:variable name="add-total" select="sum($add/Value)" /> 
     <tr> 
      <td colspan="6">Add Total</td> 
      <th><xsl:value-of select="$add-total"/></th> 
     </tr> 
     <!-- delete --> 
     <xsl:variable name="delete" select="Document[1]/Downto[not(key('MAT2PARTKEY', part_no))]" /> 
     <xsl:apply-templates select="$delete"> 
      <xsl:with-param name="section">Delete</xsl:with-param> 
     </xsl:apply-templates> 

     <xsl:variable name="delete-total" select="sum($delete/Value)" />  
     <tr> 
      <td colspan="6">Delete Total</td> 
      <th><xsl:value-of select="$delete-total"/></th> 
     </tr> 
     <!-- grand total --> 
     <tr> 
      <th colspan="6">Grand Total</th> 
      <th><xsl:value-of select="$same-total + $change-total"/></th> 
     </tr> 
    </table> 
</xsl:template> 

<xsl:template match="Downto"> 
    <xsl:param name="section"/> 
    <xsl:if test="generate-id() = generate-id(key('MATERIALBYPARTNO', part_no)[1])"> 
     <tr> 
      <td><xsl:value-of select="$section"/></td> 
      <td><xsl:value-of select="part_no"/></td> 
      <td><xsl:value-of select="rec_no"/></td>    
      <td><xsl:value-of select="desc"/></td> 
      <td><xsl:value-of select="sum(key('MAT1PARTKEY', part_no)/ext_qty)"/></td> 
      <td><xsl:value-of select="sum(key('MAT2PARTKEY', part_no)/ext_qty)"/></td> 
      <td><xsl:value-of select="sum(key('MATERIALBYPARTNO', part_no)/mat_cost)"/></td> 
     </tr> 

    </xsl:if> 
</xsl:template> 

</xsl:stylesheet> 

回答

1
<xsl:variable name="change" select="Document[1]/Downto[ 
    key('MAT2PARTKEY', part_no) and not(
     key('MATERIAL2BYKEY', concat(rec_no, '||', part_no, '||', ext_qty)) 
    ) 
]" /> 
+0

哇..我得到了我想要的。非常感謝Mark – user2822294 2014-12-04 12:04:45