2017-05-27 63 views
0

下午好!使用XSLT在新XML中按属性对元素进行分组

有了这个XML片段:

<?xml version="1.0" encoding="UTF-8"?> 
<?xml-stylesheet type="text/xsl" href="trasnf.xsl"?> 
<Shapes xmlns="namespaceProject" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xsi:schemaLocation="namespaceProject validator.xsd"> 
    <Shape id="id1"> 
      <Type>Square</Type> 
      <Data> 
       <Color>Red</Color> 
      </Data> 
     </Shape> 
    <Shape id="id2"> 
      <Type>Circle</Type> 
      <Data> 
       <Color>Blue</Color> 
      </Data> 
     </Shape> 
    <Shape id="id3"> 
      <Type>Triangle</Type> 
      <Data> 
       <Color>Red</Color> 
      </Data> 
     </Shape> 
<Shapes> 

,并希望将XML输出如:

<Shapes> 
    <Color name="Red"> 
      <Type>Square</Type> 
      <Type>Triangle</Type> 
    </Color> 
    <Color name="Blue"> 
      <Type>Circle</Type> 
    </Color> 
<Shapes> 

我怎样才能在XSLT这样做吗? 这是我从互联网和其他用户的问题中所阅读的内容中尝试过的,但它仍然无法正确打印。它只是输出文本,而不是标签,通过拖动xml到浏览器(尝试过Internet Explorer和Firefox)。

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

<xsl:template match="/"> 
<Shapes> 
     <xsl:apply-templates select="/p:Shapes/p:Shape/p:Data/p:Color[not(. = ../../preceding-sibling::p:Data/p:Color)]"/> 
</Shapes> 
</xsl:template> 

<xsl:template match="p:Color"> 
    <xsl:element name="Color"> 
     <xsl:attribute name="name"> 
      <xsl:value-of select="."/> 
     </xsl:attribute> 
     <xsl:for-each select="/p:Shapes/p:Shape[p:Data/p:Color = current()]"> 
      <xsl:element name="Type"> 
       <xsl:value-of select="p:Type"/> 
      </xsl:element> 
     </xsl:for-each> 
    </xsl:element> 
</xsl:template> 
+0

请发布尽可能少但完整的代码片段,以便我们重现问题,但在输入片段中看不到任何名称空间,因此在XSLT代码片段中使用前缀似乎没有必要。而且你甚至没有展示如何声明这个命名空间。至于“它只是输出文本”,你如何运行XSLT转换? –

+0

我已经添加了与命名空间相关的缺失部分。谢谢! –

+0

“*这是我从互联网和其他用户的问题中阅读的内容中尝试过的,*”您一直在阅读错误的来源。请阅读:http://www.jenitennison.com/xslt/grouping/muenchian.html –

回答

0

您可以更正应用模板到<xsl:apply-templates select="/p:Shapes/p:Shape/p:Data/p:Color[not(. = ../../preceding-sibling::p:Shape/p:Data/p:Color)]"/>来修复您的代码。但请注意,通过XSLT 2.0中的xsl:for-each-grouphttps://www.w3.org/TR/xslt20/#grouping-examples)或XSLT 1.0中的Muenchian grouping可以更轻松,更高效地进行分组。并且您不需要计算名称的结果元素可以简单地创建为文字,如<Type>...</Type>而不是<xsl:element name="Type">...</xsl:element>

相关问题