提前感谢您的支持。
我有以下xml和xslt
<SUBSCRIBER>
<PRODUCT_LIST>
<PRODUCT_INFO>
<ID>BA3</ID>
<PRODUCT_TYPE>Chargeable Bonus Product</PRODUCT_TYPE>
<NSN1>34178</NSN1>
<NSN2>2015-02-18 23:59:59</NSN2>
<OFFER>1104</OFFER>
<DA_UNIT>time</DA_UNIT>
<UA>1003</UA>
</PRODUCT_INFO>
<PRODUCT_INFO>
<ID>SID15</ID>
<PRODUCT_TYPE>Rate Cutter</PRODUCT_TYPE>
<NSN1>2015-12-23</NSN1>
<OFFER>1215</OFFER>
</PRODUCT_INFO>
<PRODUCT_INFO>
<ID>UseRs325GetRs25</ID>
<PRODUCT_TYPE>Usage Subscription- Traffic</PRODUCT_TYPE>
<NSN1>0</NSN1>
<NSN2>2015-02-15</NSN2>
<NSN3>2015-02-05</NSN3>
<NSN4>2015-02-15 14:01:33</NSN4>
<OFFER>1250</OFFER>
<UA>1095</UA>
<UA2>1096</UA2>
<THRESHOLD>325</THRESHOLD>
<UA_INTERVAL>10</UA_INTERVAL>
</PRODUCT_INFO>
</PRODUCT_LIST>
</SUBSCRIBER>
XSLT:
<xsl:template match="SUBSCRIBER">
<xsl:variable name="PRODUCT_TYPE" select="PRODUCT_LIST/PRODUCT_INFO[(PRODUCT_TYPE eq 'Chargeable Bonus Product') or (PRODUCT_TYPE eq 'Home Zone') or (PRODUCT_TYPE eq 'Usage Subscription- Traffic') or (PRODUCT_TYPE eq 'Telescopic Charging') or (PRODUCT_TYPE eq 'Usage Subscription- Recharge')]/PRODUCT_TYPE"/>
<xsl:for-each select="1 to count($PRODUCT_TYPE)">
<xsl:variable name="index" select="."/>
<xsl:variable name="product_name" select="$PRODUCT_TYPE[$index]"/>
<xsl:value-of select="PRODUCT_LIST/PRODUCT_INFO[(PRODUCT_TYPE eq $product_name)]/UA"/>
</xsl:for-each>
</xsl:template>
我收到以下异常,
描述:此处不能使用轴步子::元素(&#39;&#39;:PRODUCT_LIST):上下文项是原子值
请告知修复。
答案 0 :(得分:2)
错误消息说明了一切 - 当你在for-each 1 to count($PRODUCT_TYPE)
内时,上下文项(.
)是一个数字而不是一个节点,所以你不能使用一个亲戚value-of
中的XPath。您需要将for-each外部的上下文项保存在另一个变量中,然后使用相对于该路径的路径:
<xsl:variable name="dot" select="."/><!-- . here is the SUBSCRIBER -->
<xsl:for-each select="1 to count($PRODUCT_TYPE)">
<xsl:variable name="index" select="."/><!-- . here is the number -->
<xsl:variable name="product_name" select="$PRODUCT_TYPE[$index]"/>
<xsl:value-of select="$dot/PRODUCT_LIST/PRODUCT_INFO[(PRODUCT_TYPE eq $product_name)]/UA"/>
</xsl:for-each>
虽然正如其他答案所指出的那样,从长远来看,您可以更好地重构代码以使用更标准的XSLT处理方式,而不是简单地尝试移植您熟悉的for(int i = 0; i < arr.length; i++)
之类的结构更多命令式编程语言。是的,需要一段时间才能习惯更具功能性的思维方式,但从长远来看,它会带来更简单,更易于维护的代码。
答案 1 :(得分:0)
为什么不改变:
<xsl:for-each select="1 to count($PRODUCT_TYPE)">
到
<xsl:for-each select="$PRODUCT_TYPE">
然后您将处于<PRODUCT_TYPE>
的上下文中,您只需要:
<xsl:value-of select="../UA"/>
直接获取兄弟<UA>
值,而不是那么详细地说明你所做的事情。
更简单的是将第一个变量定义为:
<xsl:variable name="PRODUCT_INFO" select="PRODUCT_LIST/PRODUCT_INFO[(PRODUCT_TYPE eq 'Chargeable Bonus Product') or (PRODUCT_TYPE eq 'Home Zone') or (PRODUCT_TYPE eq 'Usage Subscription- Traffic') or (PRODUCT_TYPE eq 'Telescopic Charging') or (PRODUCT_TYPE eq 'Usage Subscription- Recharge')]"/>
然后在:
<xsl:for-each select="$PRODUCT_INFO">
达到:
<xsl:value-of select="UA"/>
答案 2 :(得分:0)
你真的不需要这里的任何变数
<xsl:template match="SUBSCRIBER">
<!-- filter on PRODUCT_LIST/PRODUCT_INFO/PRODUCT_TYPE -->
<xsl:apply-templates select="PRODUCT_LIST/PRODUCT_INFO[(PRODUCT_TYPE eq 'Chargeable Bonus Product') or (PRODUCT_TYPE eq 'Home Zone') or (PRODUCT_TYPE eq 'Usage Subscription- Traffic') or (PRODUCT_TYPE eq 'Telescopic Charging') or (PRODUCT_TYPE eq 'Usage Subscription- Recharge')]"/>
</xsl:template>
<xsl:template match="PRODUCT_INFO">
<!-- Get relevant PRODUCT_INFO values -->
<xsl:value-of select="UA"/>
</xsl:template>