我有以下XML代码(这是我试图使用的代码片段)。
<products>
<product>
<productname>Name2</productname>
<productsize measurement="ml">250</productsize>
<productsize measurement="ml">500</productsize>
<productsize measurement="ml">750</productsize>
<otherelements></otherelements>
<price size="250" packsize="1">1.25</price>
<price size="250" packsize="6">7.50</price>
<price size="250" packsize="12">7.00</price>
<price size="500" packsize="1">1.75</price>
<price size="500" packsize="6">10.50</price>
<price size="500" packsize="12">19.00</price>
<price size="750" packsize="1">2.25</price>
<price size="750" packsize="6">13.50</price>
<price size="750" packsize="12">25.00</price>
</product>
<product>
<productname>Name1</productname>
<productsize measurement="ml">250</productsize>
<productsize measurement="ml">750</productsize>
<otherelements></otherelements>
<price size="250" packsize="1">1.25</price>
<price size="250" packsize="6">7.50</price>
<price size="250" packsize="12">7.00</price>
<price size="750" packsize="1">2.25</price>
<price size="750" packsize="6">13.50</price>
<price size="750" packsize="12">25.00</price>
</product>
</products>
我想做的就是这样展示它
250ml 1=£1.25, 6=£7.50, 12=£7.00
500ml 1=£1.75, 6=£10.50, 12=£19.00
750ml 1=£2.25, 6=£13.50, 12=£25.00
但是它没有工作,这是我的XSL代码,我做错了什么,我知道这与内部for循环有关。
<xsl:for-each select="x:productsize">
<p>
<xsl:value-of select="."/>
<xsl:value-of select="@measurement"/>
</p>
<xsl:for-each select="x:price">
<xsl:if test="productsize = '@size'">
<xsl:value-of select="."/>
</xsl:if>
</xsl:for-each>
</xsl:for-each>
发布于 2014-03-19 17:36:22
首先,XML是无效的.您不能有一个名为<other elements></other elements>
的元素。你的收尾<product>
应该是</product>
。但我想这只是为这个问题写的。
主要的问题是<price>
不在<productsize>
.因此,当您在<xsl:for-each>
上运行productsize
时,您正在有效地搜索/productsize/price
试试这个..。
<xsl:for-each select="product/productsize">
<xsl:variable name="sizevar" select="."/>
<p>
<xsl:value-of select="."/>
<xsl:value-of select="@measurement"/>  
<xsl:for-each select="../price[@size=$sizevar]">
<xsl:value-of select="@packsize"/> =
<xsl:value-of select="."/>,  
</xsl:for-each>
</p>
</xsl:for-each>
它从size
中获取<productsize>
属性的值,并使用它查找具有相同size
属性的<price>
元素。
参见此用于工作演示的XMLPlayground
根据OP的注释,下面一行匹配整个文档中的所有<price>
元素.
<xsl:for-each select="//price[@size=$sizevar]">
因此,我将其更改为以下内容,它只会在父元素中找到这些元素(即,<productsize>
元素<price>
元素是其子元素)。
<xsl:for-each select="../price[@size=$sizevar]">
发布于 2014-03-19 17:46:36
假设您的源有一个名称空间,它应该在xmlns
元素或某个祖先中有一个product
声明。我假设这样的事情:
<product xmlns="your-namespace">
<productsize measurement="ml">250</productsize>
<productsize measurement="ml">500</productsize>
...
</product>
在这种情况下,还必须在XSL中声明名称空间:
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:x="your-namespace" version="1.0"> ... </xsl:stylesheet>
然后,要获得所需的结果,可以使用以下样式表:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:x="your-namespace" version="1.0">
<xsl:output method="text"/>
<xsl:template match="/">
<xsl:apply-templates select="x:product/x:productsize"/>
</xsl:template>
<xsl:template match="x:productsize">
<xsl:variable name="size" select="."></xsl:variable>
<xsl:value-of select="."/>
<xsl:value-of select="@measurement"/><xsl:text> </xsl:text>
<xsl:apply-templates select="../x:price[@size=$size]"/><xsl:text>
</xsl:text>
</xsl:template>
<xsl:template match="x:price">
<xsl:value-of select="@packsize"/><xsl:text>=£</xsl:text>
<xsl:value-of select="."/>
<xsl:if test="not(position() = last())">
<xsl:text>, </xsl:text>
</xsl:if>
</xsl:template>
</xsl:stylesheet>
至于样式表不起作用的原因,有很多可能的原因。如果名称空间被正确声明,您将尝试在price
上下文中读取productsize
,但它们不是嵌套的。您必须使用一个相对的或绝对的XPath表达式来访问脱离上下文的每个价格。我在上面使用了../price
,但它也适用于//price
。
我假设您没有发布的任何其他代码,也不能从您的示例中假设是不相关的。如果您有其他product
元素,或者如果products
实际上不是根元素,则必须修改样式表。
https://stackoverflow.com/questions/22513538
复制相似问题