一般可以写这个吗? XPATH 2.0

时间:2013-04-25 01:40:32

标签: xml xpath xpath-2.0 schematron

是否可以更一般地编写此测试。我坐了几个小时,我不知道:D。

 <pattern>
            <title>Pravidla pro měnu(CZK/USD)</title>
            <rule context="/o:objednávka/o:položky">
                <report test="(contains(o:položka[1]/o:cena/@měna,'CZK') and 
                    contains(o:položka[2]/o:cena/@měna,'USD'))or(contains(o:položka[2]/o:cena/@měna,'CZK') and 
                    contains(o:položka[1]/o:cena/@měna,'USD'))">V objednávce 
                    musí být jen jedna měna.</report>     
            </rule>

XML文档

   <?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet href="cssTrans.css" type="text/css" ?>
<?xml-model href="objednavka.sch" type="application/xml" schematypens="http://purl.oclc.org/dsdl/schematron"?>
<objednávka xmlns="urn:x-eshop:document-schemas:purchase-order">
    <položky>
        <položka kód="a">
            <název>Sekačka na trávu</název>
            <počet mj="ks">1</počet>
            <cena měna="USD">0.9</cena>
            <popis>http://example.org/sekacka.html</popis>
        </položka>
        <položka kód="d">
            <název>Travní semeno</název>
            <počet mj="kg">2.5</počet>
            <cena měna="CZK">18001</cena>
        </položka>
    </položky>
</objednávka>

2 个答案:

答案 0 :(得分:0)

使用

contains('USD|CZK|USD', string-join(o:položka/o:cena/@měna, '|'))

基于XSLT 2.0的验证:

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:o="urn:x-eshop:document-schemas:purchase-order">
 <xsl:output method="text"/>
 <xsl:strip-space elements="*"/>

 <xsl:template match="/o:objednávka/o:položky">
  <xsl:sequence select=
  "contains('USD|CZK|USD', string-join(o:položka/o:cena/@měna, '|'))"/>
 </xsl:template>
</xsl:stylesheet>

在提供的XML文档上应用此转换时:

<objednávka xmlns="urn:x-eshop:document-schemas:purchase-order">
    <položky>
        <položka kód="a">
            <název>Sekačka na trávu</název>
            <počet mj="ks">1</počet>
            <cena měna="USD">0.9</cena>
            <popis>http://example.org/sekacka.html</popis>
        </položka>
        <položka kód="d">
            <název>Travní semeno</název>
            <počet mj="kg">2.5</počet>
            <cena měna="CZK">18001</cena>
        </položka>
    </položky>
</objednávka>

评估XPath表达式并将此评估结果复制到输出中:

true

如果在此XML文档上评估相同的表达式:

<objednávka xmlns="urn:x-eshop:document-schemas:purchase-order">
    <položky>
        <položka kód="a">
            <název>Sekačka na trávu</název>
            <počet mj="ks">1</počet>
            <cena měna="USD">0.9</cena>
            <popis>http://example.org/sekacka.html</popis>
        </položka>
        <položka kód="d">
            <název>Travní semeno</název>
            <počet mj="kg">2.5</počet>
            <cena měna="USD">18001</cena>
        </položka>
    </položky>
</objednávka>

然后再次生成正确的结果:

false

答案 1 :(得分:0)

查看您的规则和实例文档,我强烈怀疑您不希望进行“包含”测试,而是进行“=”测试。人们常常想象英语短语“属性包含值”应该转换为XPath contains(@att, 'val'),但这是错误的;它应该是@att = 'val'

我认为你要表达的约束是有两个položka元素,其中一个,cena / @měna属性的值为USD,而另一个,它的值为CZK。我会表达为

o:položka/o:cena/@měna ='CZK' and o:položka/o:cena/@měna = 'USD'

记住在XPath中,“=”是存在的:a/b/c='USD'表示a/b/c选择的至少一个节点的值为'USD'