【问题标题】:How do I find duplicate data in xml document using XQuery?如何使用 XQuery 在 xml 文档中查找重复数据?
【发布时间】:2010-10-01 12:15:41
【问题描述】:

我在 MarkLogic xml 数据库中有一堆文档。一份文件有:

<colors>
  <color>red</color>
  <color>red</color>
</colors>

拥有多种颜色不是问题。有多种颜色都是红色是一个问题。如何找到有重复数据的文档?

【问题讨论】:

    标签: xml xquery duplicate-data marklogic


    【解决方案1】:

    MarkLogic 返回的所有内容都只是一个节点序列,因此我们可以计算整体的序列大小,并将其与不同值序列的计数进行比较。如果它们不是不同的,它们就是重复的,并且你有你的子集。

    for $c in doc()//colors
    where fn:count($c/color) != fn:count(fn:distinct-values($c/color))
    return $c
    

    【讨论】:

    • 根据您的扩​​展需求,这将很快耗尽内存。请参阅下面的仅索引方法
    【解决方案2】:

    这应该可以解决问题。我对 MarkLogic 不太熟悉,所以第一行获取文档集可能是错误的。这将返回具有相同字符串值的 2 个或更多颜色元素的所有文档。

    for $doc in doc()
    let $colors = $doc//color/string(.)
    where some $color in $colors
          satisfies count($colors[. = $color] > 1)
    return doc()
    

    【讨论】:

    • 遍历所有文档是唯一的方法吗?
    【解决方案3】:

    或者你可以完全用索引来完成它:)

    for $c in doc()//colors 可能会在较大的数据集上创建 EXPANDED TREE CACHE 错误。

    当数据量很大时,这里有一个稍微复杂的攻击方法,确保 URI Lexicon 已打开,然后添加 元素范围索引元素 color 并计算在某处重复的不同颜色值。然后仅循环遍历具有此颜色的文档,并计算文档中感兴趣颜色的项目频率计数。如果您的频率超过 1,则该文档需要重复数据删除。

    let $qn := xs:QName("color")
    let $colorsWithItemFreq := cts:element-values($qn, (), ("ascending", "item-order", "item-frequency"))
    let $colorsOfInterest := 
        for $color at $i in cts:element-values($qn, (), ("ascending", "item-order", "fragment-frequency"))
        let $fragFrequency := cts:frequency($color)
        let $itemFrequency := cts:frequency($colorsWithItemFreq[$i])
        where $itemFrequency gt $fragFrequency
        return 
            $color
    
    for $uri in cts:uris( (), ("document"), cts:element-value-query($qn, $colorsOfInterest)
    let $colorsWithDuplicationInThisDoc :=
        for $color in cts:element-values($qn, (), ("item-frequency"), cts:document-query($uri) )
        where $color = $colorsOfInterest and cts:frequency($color) gt 1
        return
            $color
    where fn:count( $colorsWithDuplicationInThisDoc ) gt 1
    return
        $uri
    

    希望对您有所帮助。

    【讨论】:

      【解决方案4】:

      对于这个 XML:

      <?xml version="1.0"?>
      <colors>
          <color>Red</color>
          <color>Red</color>
          <color>Blue</color>
      </colors>
      

      使用这个 XSD:

      <?xml version="1.0"?>
      <xsl:stylesheet version="1.0"
        xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
      
          <xsl:output method = "text" />  
          <xsl:strip-space elements="*"/>
      
          <xsl:template match="colors">
      
              <xsl:for-each select="color">
                  <xsl:variable name="node_color" select="text()"/>
                  <xsl:variable name="numEntries" select="count(../color[text()=$node_color])"/>
                  <xsl:if test="$numEntries &gt; 1">
                      <xsl:text>Color value of </xsl:text><xsl:value-of select="."/><xsl:text> has multiple entries &#xa;</xsl:text>      
                  </xsl:if>
              </xsl:for-each>
          </xsl:template>
      </xsl:stylesheet>
      

      我得到了这个输出:

      Color value of Red has multiple entries 
      Color value of Red has multiple entries 
      

      这样至少会找到它们,但它会报告每次出现的重复颜色,而不仅仅是每个重复的颜色。

      【讨论】:

        猜你喜欢
        • 2015-11-02
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-08-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多