我試圖使用XSLT將1個XML文件轉換爲另一個,其中生成的XML文件是執行查詢的結果。不幸的是,據我所知,XSLT中的變量是不可變的,不能改變。我想知道是否有其他方法可以將這些值相加,這樣我就可以得到相關部分返回的任何查詢的總值。雖然XSLT變量是不可變的,但是嘗試增加一個變量
正如您在原始XML文件中看到的那樣,總數中包含了每個條目中所有年齡段編號的總計值。我使用XSLT查詢根據所查詢的$ AGE_GROUP1和$ AGE_GROUP2的年齡範圍提取出不同的年齡段,但由於任何聲明的變量都是不可變的,所以我想不出一種方法來將所查詢的年齡段值加起來。
以下是源XML文件:
<?xml version="1.0" encoding="UTF-8"?>
<Replacements>
<Entry>
<Year>2005</Year>
<Month>DEC</Month>
<Reason>Blemish on Card</Reason>
<Age>
<Group>
<Range>Total</Range>
<value>16</value>
</Group>
<Group>
<Range>16-17</Range>
<value>3</value>
</Group>
<Group>
<Range>18-25</Range>
<value>12</value>
</Group>
<Group>
<Range>26-29</Range>
<value>1</value>
</Group>
</Age>
</Entry>
<Entry>
<Year>2005</Year>
<Month>DEC</Month>
<Reason>Damaged</Reason>
<Age>
<Group>
<Range>Total</Range>
<value>7</value>
</Group>
<Group>
<Range>16-17</Range>
<value>6</value>
</Group>
<Group>
<Range>18-25</Range>
<value>0</value>
</Group>
<Group>
<Range>26-29</Range>
<value>1</value>
</Group>
</Age>
</Entry>
</Replacements>
下面的XSLT僅提取有關2 3個年齡組(只提取年齡組從14歲到24),所以年齡組的1對在原始數據集的每個條目不輸出到生成的XML文件:
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="2.0">
<xsl:variable name = "QUERY_YEAR1" select = "2005" />
<xsl:variable name = "QUERY_YEAR2" select = "2007" />
<xsl:variable name = "AGE_GROUP1" select = "14" />
<xsl:variable name = "AGE_GROUP2" select = "24" />
<xsl:variable name = "TOTAL" select = "0" />
<xsl:output method="xml" indent="yes" />
<xsl:strip-space elements="*" />
<xsl:template match="/">
<xsl:for-each select="Replacements/Entry">
<xsl:if test="$QUERY_YEAR1 <= Year/text() and $QUERY_YEAR2 >= Year/text()">
<Entry>
<Year>
<xsl:value-of select="Year/text()" />
</Year>
<Month>
<xsl:value-of select="Month/text()" />
</Month>
<Reason>
<xsl:value-of select="Reason/text()" />
</Reason>
<xsl:for-each select="Age/Group">
<!-- $AGE_GROUP1 < 16 & 17, $AGE_GROUP2 > 16 & 17 for age group 16-17 (e.g. $AGE_GROUP1 = 14 & $AGE_GROUP2 = 30 -->
<xsl:if test="$AGE_GROUP1 <= number(substring(Range/text(), 1, 2)) and $AGE_GROUP1 <= number(substring(Range/text(), 4, 2)) and $AGE_GROUP2 >= number(substring(Range/text(), 1, 2)) and $AGE_GROUP2 >= number(substring(Range/text(), 4, 2)) and not(Range/text() = 'Total') and not(Range/text() = '80+')">
<!-- Add to $TOTAL value -->
<xsl:variable name = "TOTAL" select = "number($TOTAL) + number(value/text())" />
<AgeGroup>
<Range>
<xsl:value-of select="Range/text()" />
</Range>
<value>
<xsl:value-of select="value/text()" />
</value>
</AgeGroup>
</xsl:if>
<!-- $AGE_GROUP1 < 30 & 39, $AGE_GROUP2 = 30 & < 39 for age group 30-39 (e.g. $AGE_GROUP1 = 14 & $AGE_GROUP2 = 30 -->
<!-- $AGE_GROUP1 < 26 & 29, $AGE_GROUP2 > 26 & < 29 for age group 26-29 (e.g. $AGE_GROUP1 = 19 & $AGE_GROUP2 = 27 -->
<xsl:if test="$AGE_GROUP1 <= number(substring(Range/text(), 1, 2)) and $AGE_GROUP1 <= number(substring(Range/text(), 4, 2)) and $AGE_GROUP2 >= number(substring(Range/text(), 1, 2)) and $AGE_GROUP2 <= number(substring(Range/text(), 4, 2)) and not(Range/text() = 'Total') and not(Range/text() = '80+')">
<!-- Add to $TOTAL value -->
<xsl:variable name = "TOTAL" select = "number($TOTAL) + number(value/text())" />
<AgeGroup>
<Range>
<xsl:value-of select="Range/text()" />
</Range>
<value>
<xsl:value-of select="value/text()" />
</value>
</AgeGroup>
</xsl:if>
<!-- $AGE_GROUP1 > 18 & < 25, $AGE_GROUP2 > 18 & 25 for age group 18-25 (e.g. $AGE_GROUP1 = 19 & $AGE_GROUP2 = 27 -->
<xsl:if test="$AGE_GROUP1 >= number(substring(Range/text(), 1, 2)) and $AGE_GROUP1 <= number(substring(Range/text(), 4, 2)) and $AGE_GROUP2 >= number(substring(Range/text(), 1, 2)) and $AGE_GROUP2 >= number(substring(Range/text(), 4, 2)) and not(Range/text() = 'Total') and not(Range/text() = '80+')">
<!-- Add to $TOTAL value -->
<xsl:variable name = "TOTAL" select = "number($TOTAL) + number(value/text())" />
<AgeGroup>
<Range>
<xsl:value-of select="Range/text()" />
</Range>
<value>
<xsl:value-of select="value/text()" />
</value>
</AgeGroup>
</xsl:if>
</xsl:for-each>
<!-- Total calculation for all values within returned age groups -->
<AgeGroup>
<Range>
<xsl:value-of select="'Total'" />
</Range>
<value>
<xsl:value-of select="$TOTAL" />
</value>
</AgeGroup>
</Entry>
</xsl:if>
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
我現在得到的是下面的,不具有所提取的年齡組值的總價值,因爲我不能分配變量每個關口$ TOTAL:
<?xml version="1.0" encoding="UTF-8"?>
<Entry>
<Year>2005</Year>
<Month>DEC</Month>
<Reason>Blemish on Card</Reason>
<AgeGroup>
<Range>16-17</Range>
<value>3</value>
</AgeGroup>
<AgeGroup>
<Range>18-25</Range>
<value>12</value>
</AgeGroup>
<AgeGroup>
<Range>Total</Range>
<value>0</value>
</AgeGroup>
</Entry>
<Entry>
<Year>2005</Year>
<Month>DEC</Month>
<Reason>Damaged</Reason>
<AgeGroup>
<Range>16-17</Range>
<value>6</value>
</AgeGroup>
<AgeGroup>
<Range>18-25</Range>
<value>0</value>
</AgeGroup>
<AgeGroup>
<Range>Total</Range>
<value>0</value>
</AgeGroup>
</Entry>
我需要的是這樣的:
<?xml version="1.0" encoding="UTF-8"?>
<Entry>
<Year>2005</Year>
<Month>DEC</Month>
<Reason>Blemish on Card</Reason>
<AgeGroup>
<Range>16-17</Range>
<value>3</value>
</AgeGroup>
<AgeGroup>
<Range>18-25</Range>
<value>12</value>
</AgeGroup>
<AgeGroup>
<Range>Total</Range>
<value>15</value>
</AgeGroup>
</Entry>
<Entry>
<Year>2005</Year>
<Month>DEC</Month>
<Reason>Damaged</Reason>
<AgeGroup>
<Range>16-17</Range>
<value>6</value>
</AgeGroup>
<AgeGroup>
<Range>18-25</Range>
<value>0</value>
</AgeGroup>
<AgeGroup>
<Range>Total</Range>
<value>6</value>
</AgeGroup>
</Entry>
我用做XSLT的命令是這樣的:java -jar saxon9he.jar sample1.xml sample1.xslt > out.xml
我只是想知道如果任何人有任何想法,我怎麼能只要輸入if條件就可以添加類似於XSLT中看到的值,以便將該年齡段的值添加到總數中,並且總數可以在輸出XML文件內返回?
謝謝!那是我需要的。如果我得到了原始XML文件中的另一個年齡組, 80+ ,我該怎麼辦? –
iteong
我已經對答案進行了編輯,希望能夠展示如何調整表達式以應對此問題。 –
完美!它很棒!愛堆棧溢出= D – iteong