2013-07-30 42 views
0

我已經開始使用XSL並且遇到了唯一的動態列數據問題。我已閱讀過類似的問題,但這種情況似乎有所不同,所以我沒有看到這些解決方案在這個問題上的應用。帶鍵的XSL動態表列數據

我有以下的樣本數據集可以增長或與大量的<ID><Date>值縮水:

<Report> 
    <DataSets> 
    <Data> 
     <ID>1</ID> 
     <Date>201211</Date> 
    </Data> 
    <Data> 
     <ID>1</ID> 
     <Date>201211</Date> 
    </Data> 
    <Data> 
     <ID>1</ID> 
     <Date>201210</Date> 
    </Data> 
    <Data> 
     <ID>2</ID> 
     <Date>201209</Date> 
    </Data> 
    <Data> 
     <ID>1</ID> 
     <Date>201208</Date> 
    </Data> 
    <Data> 
     <ID>2</ID> 
     <Date>201208</Date> 
    </Data> 
    <Data> 
     <ID>3</ID> 
     <Date>201208</Date> 
    </Data> 
    <Data> 
     <ID>3</ID> 
     <Date>201208</Date> 
    </Data> 
    </DataSets> 
</Report> 

我試圖獲得XSL代碼來生成如下表:

ID 201208 201209 201210 201211 
1  1  0  1  2 
2  1  1  0  0 
3  2  0  0  0 

這些列是動態的,列標題是<Date>元素的唯一值。這些行是唯一ID的集合,數據是每個<Date>的所述<ID>的計數。我正在努力的是爲每個<Date>動態創建<ID>的計數。

到目前爲止,我有以下XSL文件使用生成表的鍵,但正如您可以看到日期是硬編碼atm。

<?xml version="1.0" encoding="UTF-8"?> 
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
       version="1.0" > 

<xsl:template match ="/" > 
<html> 
    <body> 
    <xsl:apply-templates select="Report/DataSets"/> 
    </body> 
</html> 
</xsl:template> 

<xsl:key name="Data_ID" match="Data" use="ID" /> 
<xsl:key name="Data_D" match="Data" use="Date"/> 
<xsl:template match="Report/DataSets" > 
<table> 
    <tr> 
    <th>ID</th> 
    <xsl:for-each select="Data[generate-id(.) = generate-id(key('Data_D', Date)[1])]"> 
     <xsl:sort select="Date"/> 
     <!-- Dynamically add headers for each Date Column --> 
     <th><xsl:value-of select="Date"/></th> 
    </xsl:for-each> 
    </tr> 
    <xsl:for-each select="Data[generate-id(.) = generate-id(key('Data_ID', ID)[1])]"> 
    <xsl:sort select="ID"/> 
    <tr> 
    <td><xsl:value-of select="ID"/></td> 
    <!-- Dynamically count IDs for each Date Column --> 
    <!-- How to do this step? --> 
    <td><xsl:value-of select="count(key('Data_ID', ID)[Date='201208'])"/></td> 
    <td><xsl:value-of select="count(key('Data_ID', ID)[Date='201209'])"/></td> 
    <td><xsl:value-of select="count(key('Data_ID', ID)[Date='201210'])"/></td> 
    <td><xsl:value-of select="count(key('Data_ID', ID)[Date='201211'])"/></td> 
    </tr> 
    </xsl:for-each> 
</table> 
</xsl:template> 
</xsl:stylesheet> 

現在需要更換這些硬編碼的條目

<td><xsl:value-of select="count(key('Data_ID', ID)[Date='201208'])"/></td> 
<td><xsl:value-of select="count(key('Data_ID', ID)[Date='201209'])"/></td> 
<td><xsl:value-of select="count(key('Data_ID', ID)[Date='201210'])"/></td> 
<td><xsl:value-of select="count(key('Data_ID', ID)[Date='201211'])"/></td> 

動態代碼?

回答

0

您可以使用同一種for-each您所使用的標題

<!-- store the full set of Data in a variable - we will need it inside the for-eaches --> 
    <xsl:variable name="allData" select="Data"/> 
    <xsl:for-each select="$allData[generate-id(.) = generate-id(key('Data_ID', ID)[1])]"> 
    <xsl:sort select="ID"/> 
    <xsl:variable name="currentId" select="ID" /> 
    <tr> 
    <td><xsl:value-of select="$currentId"/></td> 
    <!-- Dynamically count IDs for each Date Column --> 
    <xsl:for-each select="$allData[generate-id(.) = generate-id(key('Data_D', Date)[1])]"> 
     <xsl:sort select="Date"/> 
     <td> 
     <xsl:value-of select="count(key('Data_ID', $currentId)[Date=current()/Date])"/> 
     </td> 
    </xsl:for-each> 
    </tr> 
    </xsl:for-each> 

這裏的竅門是從外for-eachID保存在一個變量,所以你可以訪問它,而你在裏面內部for-each

甲可能更有效的替代方案將是,以限定在兩個ID和日期第三密鑰

<xsl:key name="Data_ID_D" match="Data" use="concat(ID, '|', Date)" /> 

這將簡化count表達

<xsl:for-each select="$allData[generate-id(.) = generate-id(key('Data_D', Date)[1])]"> 
    <xsl:sort select="Date"/> 
    <td> 
    <xsl:value-of select="count(key('Data_ID_D', concat($currentId, '|', Date)))"/> 
    </td> 
</xsl:for-each> 
+0

這種方法似乎不工作,我得到一張空桌子。額外的'for-each'的問題是上下文已經設置好了,並且你沒有看到你可以移回路徑來爲日期創建一個新的集合。另外,嘗試組合這兩個鍵似乎並不奏效,因爲這些鍵需要獨立存在,並將結果合併到非唯一的行條目中。 – JMO

+0

@JMO好點。您需要將外部上下文保存在另一個變量中,以便您可以在兩個for-each選項上執行Muenchian技巧(請參閱編輯)。 –

+0

啊,是的,它做到了。完美的作品,謝謝。 – JMO