xsl-list
[Top] [All Lists]

Re: how to remove duplicates from more than one file?

2002-12-09 03:24:26
Hi Mike,

"Michael Kay" <michael(_dot_)h(_dot_)kay(_at_)ntlworld(_dot_)com> wrote in 
message
news:002301c29f67$9180a410$6401a8c0(_at_)pcukmka(_dot_)(_dot_)(_dot_)
Your code works fine with Saxon. For reference, here is the complete
stylesheet:

<?xml version="1.0" encoding="iso-8859-1"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform";>
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1"
indent="yes"/>

<xsl:key name="items" match="item" use="@name"/>

<xsl:variable name="source">
     <xsl:copy-of select="document('test1.xml')//item |
document('test2.xml')//item"/>
</xsl:variable>

<xsl:template match="/">
<xsl:for-each select="$source">

This will require the xxx:node-set() extension function, won't it?

And probably copying of all xml documents into a temporary tree can be
avoided?

     <xsl:for-each
select="//item[generate-id(.)=generate-id(key('items', @name)[1])]">
         <xsl:copy-of select="."/>
     </xsl:for-each>
</xsl:for-each>
</xsl:template>

</xsl:stylesheet>

I can't think of any better way of doing it in XSLT 1.0. Neither the
Muenchian approach nor the preceding-sibling approach to elimination
of
duplicates can handle multiple documents directly.

Here's one way:

Using FXSL, the following transformation:

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

    <xsl:import href="foldl.xsl"/>

    <xsl:output indent="yes" omit-xml-declaration="yes"/>
    <mytestElem:mytestElem/>
    <xsl:template match="/">
      <xsl:variable name="vFun-testElem"
                    select="document('')/*/mytestElem:*[1]"/>

      <xsl:call-template name="foldl">
        <xsl:with-param name="pFunc" select="$vFun-testElem"/>
        <xsl:with-param name="pA0" select="/.."/>
        <xsl:with-param name="pList"
                   select="document('testDistinct11.xml')/itemList/item
                         | document('testDistinct22.xml')/itemList/item
                         |
document('testDistinct33.xml')/itemList/item"
        />
      </xsl:call-template>
    </xsl:template>

    <xsl:template match="mytestElem:*">
      <xsl:param name="arg1" select="/.."/>
      <xsl:param name="arg2" select="/.."/>

      <xsl:copy-of select="$arg1"/>
      <xsl:if test="not($arg2/@name = $arg1/@name)">
        <xsl:copy-of select="$arg2"/>
      </xsl:if>
    </xsl:template>
</xsl:stylesheet>

when applied to a dummy source xml:
</t>

and when the referenced documents 'testDistinct11.xml',
'testDistinct22.xml', 'testDistinct33.xml' have the contents provided
in
the original message, then the result is:

<item name="one">value_1</item>
<item name="two">value_2</item>
<item name="three">value_3</item>
<item name="seven">value_7</item>


=====
Cheers,

Dimitre Novatchev.
http://fxsl.sourceforge.net/ -- the home of FXSL

__________________________________________________
Do you Yahoo!?
Yahoo! Mail Plus - Powerful. Affordable. Sign up now.
http://mailplus.yahoo.com

 XSL-List info and archive:  http://www.mulberrytech.com/xsl/xsl-list