首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用xslt查找重复节点

使用xslt查找重复节点
EN

Stack Overflow用户
提问于 2016-10-13 20:01:22
回答 3查看 2.1K关注 0票数 1

我需要查找重复的和空的节点,而不是从XML中删除它们,因此我在XSL下面编写,并且能够通过读取XML.But无法获得结果(如果存在重复节点)来获得空节点的列表。需要你的帮助才能实现这一点。

下面是输入的XML:

代码语言:javascript
复制
    <p:Organisation xmlns:p="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd HeaderRecords.xsd ">
  <p:EMP>
    <p:ID>123</p:ID>
    <p:Name>uday</p:Name>
    <p:Designation>SoftwareEng</p:Designation>
    <p:ExpertiseIn>SOA,OSB,TIBCO</p:ExpertiseIn>
  </p:EMP>
  <p:ASSETS>
    <p:ASSET>
      <p:AssetID>1000</p:AssetID>
      <p:Name>Ego</p:Name>
      <p:InUse>yes</p:InUse>
      <p:AssignedDate>2005</p:AssignedDate>
    </p:ASSET>
    <p:ASSET>
      <p:AssetID>2000</p:AssetID>
      <p:Name>HP</p:Name>
      <p:InUse></p:InUse>
      <p:AssignedDate>2002</p:AssignedDate>
    </p:ASSET>
    <p:ASSET>
      <p:AssetID>3000</p:AssetID>
      <p:Name>Dell</p:Name>
      <p:InUse>yes</p:InUse>
      <p:AssignedDate>2010</p:AssignedDate>
    </p:ASSET>
    <p:ASSET>
      <p:AssetID>4000</p:AssetID>
      <p:Name></p:Name>
      <p:InUse>yes</p:InUse>
      <p:AssignedDate>2009</p:AssignedDate>
    </p:ASSET>
    <p:ASSET>
      <p:AssetID>3000</p:AssetID>
      <p:Name>Lenovo</p:Name>
      <p:InUse>yes</p:InUse>
      <p:AssignedDate>2011</p:AssignedDate>
    </p:ASSET>
  </p:ASSETS>
</p:Organisation>

下面是如果我看到任何空节点所得到的当前输出:

代码语言:javascript
复制
InUse in Line- 2 with Position-3 is empty               


Name in Line- 4 with Position-2 is empty    

预期产出如下:

代码语言:javascript
复制
    InUse in Line- 2 with Position-3 is empty               

   Name in Line- 4 with Position-2 is empty             

   Found Duplicate Asset ID's

下面是我工作过并能够获得直到列表中的空节点的XSLT:

代码语言:javascript
复制
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:p="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd">
<xsl:output omit-xml-declaration="yes" />

<xsl:template match="/">
    <xsl:apply-templates mode="rule1"
        select="p:Organisation/p:EMP/p:ID">
    </xsl:apply-templates>
    <xsl:apply-templates mode="rule2"
        select="p:Organisation/p:EMP/p:Name">
    </xsl:apply-templates>
    <xsl:apply-templates mode="rule3"
        select="p:Organisation/p:EMP/p:Designation">
    </xsl:apply-templates>
    <xsl:apply-templates mode="rule4"
        select="p:Organisation/p:EMP/p:ExpertiseIn">
    </xsl:apply-templates>

    <xsl:apply-templates mode="rule5"
        select="p:Organisation/p:ASSETS">
    </xsl:apply-templates>

</xsl:template>

                                            <!-- Employee data Validation -->

<xsl:template match="p:ID" mode="rule1">
    <xsl:if test="current()  = ''">
    Employee ID is empty.
    </xsl:if>
</xsl:template>
<xsl:template match="p:Name" mode="rule2">
    <xsl:if test="current() = ''">
    Employee Name is empty.
    </xsl:if>           
</xsl:template>
<xsl:template match="p:Designation" mode="rule3">
    <xsl:if test="current() = ''">
    Employee Designation is empty.
    </xsl:if>   
</xsl:template>
<xsl:template match="p:ExpertiseIn" mode="rule4">
    <xsl:if test="current() = ''">
    ExpertiseIn data can't be empty.
    </xsl:if>       
</xsl:template> 

                                            <!-- Assets data Validation -->

<xsl:template match="p:ASSETS/*" mode='rule5'>
    <xsl:variable name="i" select="count(preceding-sibling::*)+1" />
    <xsl:for-each select="child::*">
        <xsl:if test="current() = '' ">         
        <xsl:value-of select="local-name()" /> in Line- <xsl:value-of select="$i" /> with Position-<xsl:value-of select="count(preceding-sibling::*)+1" /> is empty             
        </xsl:if>
    </xsl:for-each>
</xsl:template> 

请帮助我找到重复的节点也。

谢谢你们伸出援手。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2016-10-13 21:33:01

我刚刚发现,即使是我们也可以使用generate()概念来实现这个需求,如下所示:

代码语言:javascript
复制
<xsl:if test="p:ASSETS/p:ASSET[generate-id()= generate-id(key('asset',p:AssetID)[2])]">Found Duplicate Asset ID's</xsl:if>
票数 0
EN

Stack Overflow用户

发布于 2016-10-14 02:12:41

这个简短而简单的转换会产生一个空格分隔的列表,其中包含所有具有重复值( p:AssetID )的元素()。

代码语言:javascript
复制
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:p="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd">
 <xsl:output method="text"/>
 <xsl:key name="kAsseIdByVal" match="p:AssetID" use="."/>

  <xsl:template match="p:AssetID[generate-id()=generate-id(key('kAsseIdByVal', .)[2])]">
    <xsl:value-of select="concat(., ' ')"/>
  </xsl:template>
  <xsl:template match="text()"/>
</xsl:stylesheet>

当应用于此XML文档时,(提供了一个+一个多个pAsset元素来多一个重复值组):

代码语言:javascript
复制
<p:Organisation xmlns:p="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd HeaderRecords.xsd ">
    <p:EMP>
        <p:ID>123</p:ID>
        <p:Name>uday</p:Name>
        <p:Designation>SoftwareEng</p:Designation>
        <p:ExpertiseIn>SOA,OSB,TIBCO</p:ExpertiseIn>
    </p:EMP>
    <p:ASSETS>
        <p:ASSET>
            <p:AssetID>1000</p:AssetID>
            <p:Name>Ego</p:Name>
            <p:InUse>yes</p:InUse>
            <p:AssignedDate>2005</p:AssignedDate>
        </p:ASSET>
        <p:ASSET>
            <p:AssetID>2000</p:AssetID>
            <p:Name>HP</p:Name>
            <p:InUse></p:InUse>
            <p:AssignedDate>2002</p:AssignedDate>
        </p:ASSET>
        <p:ASSET>
            <p:AssetID>3000</p:AssetID>
            <p:Name>Dell</p:Name>
            <p:InUse>yes</p:InUse>
            <p:AssignedDate>2010</p:AssignedDate>
        </p:ASSET>
        <p:ASSET>
            <p:AssetID>4000</p:AssetID>
            <p:Name></p:Name>
            <p:InUse>yes</p:InUse>
            <p:AssignedDate>2009</p:AssignedDate>
        </p:ASSET>
        <p:ASSET>
            <p:AssetID>3000</p:AssetID>
            <p:Name>Lenovo</p:Name>
            <p:InUse>yes</p:InUse>
            <p:AssignedDate>2011</p:AssignedDate>
        </p:ASSET>
        <p:ASSET>
            <p:AssetID>4000</p:AssetID>
            <p:Name></p:Name>
            <p:InUse>yes</p:InUse>
            <p:AssignedDate>2009</p:AssignedDate>
        </p:ASSET>
    </p:ASSETS>
</p:Organisation>

想要的,正确的结果产生

代码语言:javascript
复制
3000 4000 
票数 1
EN

Stack Overflow用户

发布于 2016-10-13 21:00:57

为了将示例最小化到当前的问题,请考虑以下样式表:

XSLT1.0

代码语言:javascript
复制
<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:p="http://www.tibco.com/schemas/prjDelimeter/Schema/Schema2.xsd">
<xsl:output method="text" encoding="UTF-8" />

<xsl:key name="asset" match="p:ASSET" use="p:AssetID" />

<xsl:template match="/p:Organisation">
    <!-- other stuff -->
    <xsl:if test="p:ASSETS/p:ASSET[count(key('asset', p:AssetID)) > 1]">Found Duplicate Asset ID's</xsl:if>
</xsl:template>

</xsl:stylesheet>
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/40029916

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档