Не эквивалентен в выражении XPath - PullRequest
5 голосов
/ 14 августа 2010

Я работаю над разработкой XSL и мне нужно знать эквивалент NOT IN в XPATH.Я представляю XML и XSL в простейшем формате, понятном для всех.

<?xml-stylesheet type="text/xsl" href="XSL.xsl"?>
<Message>
    <Customers>
        <Customer pin="06067">1</Customer>
        <Customer pin="06068">2</Customer>
        <Customer pin="06069">3</Customer>
        <Customer pin="06070">4</Customer>
        <Customer pin="06072">5</Customer>
    </Customers>
    <Addresses>
        <Address pin1="06067">A</Address>
        <Address pin1="06068">B</Address>
        <Address pin1="06069">C</Address>
    </Addresses>
</Message>

XSL

<xsl:template match="/Message">
    <html>
        <body>
            <h4>Existing Customers</h4>
            <table>
                <xsl:apply-templates select="//Customers/Customer[@pin = //Addresses/Address/@pin1]"></xsl:apply-templates>
            </table>

            <h4>New Customers</h4>
            <table>
                <!--This place need to be filled with new customers-->
            </table>
        </body>
    </html>
</xsl:template>

<xsl:template match="Customer" name="Customer">
    <xsl:variable name="pin" select="./@pin"></xsl:variable>
    <tr>
        <td>
            <xsl:value-of select="."/>
            <xsl:text> is in </xsl:text>
            <xsl:value-of select="//Addresses/Address[@pin1=$pin]"/>
        </td>
    </tr>
</xsl:template>

Ввышеупомянутый XSLT, в области комментариев, мне нужно сопоставить и отобразить клиентов, чей адрес не существует в узле Адреса / Адреса.

Пожалуйста, помогите найти выражение XPath, которое соответствует клиентам, которые НЕ ВАдресный узел установлен.(Любой заместитель может также помочь)

Ответы [ 2 ]

7 голосов
/ 14 августа 2010

В XPath 1.0:

/Message/Customers/Customer[not(@pin=/Message/Addresses/Address/@pin1)]
4 голосов
/ 14 августа 2010

Альтернативой хорошему ответу @ Alejandro , за который я проголосовал, является следующее преобразование, в котором используются ключи, и будет более эффективным, если число существующих клиентов велико :

<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output omit-xml-declaration="yes" indent="yes"/>

    <xsl:key name="kexistingByPin"
         match="Address" use="@pin1"/>

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

 <xsl:template match="/">
   <xsl:apply-templates select=
    "*/*/Customer[not(key('kexistingByPin', @pin))]"/>
 </xsl:template>
</xsl:stylesheet>

когда это преобразование применяется к предоставленному XML-документу :

<Message>
    <Customers>
        <Customer pin="06067">1</Customer>
        <Customer pin="06068">2</Customer>
        <Customer pin="06069">3</Customer>
        <Customer pin="06070">4</Customer>
        <Customer pin="06072">5</Customer>
    </Customers>
    <Addresses>
        <Address pin1="06067">A</Address>
        <Address pin1="06068">B</Address>
        <Address pin1="06069">C</Address>
    </Addresses>
</Message>

желаемый, правильный ответ выдается :

<Customer pin="06070">4</Customer>
<Customer pin="06072">5</Customer>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...