2013-02-14 79 views
0

我正在努力解决以下问题。 希望你们任何一个人建议或指导我解决这个问题。根据xslt中的当前节点值更改以前的NODE值

我有一个低于伪xsd类型的有效载荷。

<element name=Main maxCoccurs=unbounded> 
     <complexType> 
      <element name=input1/> 
      <element name=input2/> 
      <element name=input3/> 
      <element name=input4/> 
      <element name=input5/> 
      <element name=inside/> 
       <element name=username/> 
       <element name=address/> 
     </complextype> 
    <element> 

主是一个可重复的元素。 我想检查用户名,如果所有节点的用户名值不相等,那么我需要为第一个节点用户名分配空白值。

我该如何在转换中做到这一点?

我正在尝试以下操作: 在变量中获取firt用户名,然后使用for-each来检查所有用户名。 如果它不等于....但我不能将空值分配给第一个节点,因为我在某些地方在第n个节点的用户名。

我在想使用一个变量来表示不匹配= true(),但是xslt无法让我们在声明后对变量进行更改。 所以即使这个选项被排除。

我该如何做到这一点? 帮我解决这个问题..

希望我很清楚。

干杯 Chandru

+0

使用XSLT 1.0或XSLT 2.0? – 2013-02-14 10:18:45

+0

您已将此标记为xslt 1.0和2.0 - 您确实需要哪一个? – 2013-02-14 10:19:04

回答

0

假设foomain元素的父元素的名称可以使用

<xsl:stylesheet 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    version="2.0"> 

<xsl:template match="@* | node()"> 
    <xsl:copy> 
    <xsl:apply-templates select="@* , node()"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="foo[some $m in main satisfies $m/username != main/username]/main[1]/username"> 
    <xsl:copy/> 
</xsl:template> 

</xsl:stylesheet> 

下面是一些输入样本:

<root> 
    <foo> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u1</username> 
     <address/> 
    </main> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u1</username> 
     <address/> 
    </main> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u2</username> 
     <address/> 
    </main> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u1</username> 
     <address/> 
    </main> 
    </foo> 
</root> 

当样式表应用撒克逊9.4,我得到的输出是

<root> 
    <foo> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username/> 
     <address/> 
    </main> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u1</username> 
     <address/> 
    </main> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u2</username> 
     <address/> 
    </main> 
    <main> 
     <input1/> 
     <input2/> 
     <input3/> 
     <input4/> 
     <input5/> 
     <inside/> 
     <username>u1</username> 
     <address/> 
    </main> 
    </foo> 
</root> 

,其中第一mainusername现在是空的,因为有一个mainusername是从其他的不同。

由于答案已被接受,我有点困惑,但评论说你需要一个XSLT 1.0解决方案。我将在下面提供一个XSLT 1.0样式表:

<xsl:stylesheet 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    version="1.0"> 

<xsl:template match="@* | node()"> 
    <xsl:copy> 
    <xsl:apply-templates select="@* | node()"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="foo[main[username != ../main/username]]/main[1]/username"> 
    <xsl:copy/> 
</xsl:template> 

</xsl:stylesheet> 
+0

谢谢你的回复。我现在删除了xslt 1.0标签。 @Martin,我觉得理解你的解决方案并不困难。跟你说再见吗? – user2071463 2013-02-14 13:00:16

+0

你说:“我想检查用户名,如果所有节点的用户名值不相等,那么我需要为第一个节点用户名分配空白值”。对于使用XSLT 2.0的人来说,如果符合条件,就可以为第一个'main'('main [1]')元素的'用户名'孩子编写一个模板。但是我认为我用'not(=)'写了错误的谓词检查。我将编辑并提供经过测试的代码示例。 – 2013-02-14 13:51:03

+0

非常感谢Martin ......我很抱歉,因为xslt版本是1.0而不是2.0。我试过你提供给我的解决方案,但不幸的是它没有为我工作.. :( – user2071463 2013-02-15 05:19:34

相关问题