2010-09-01 14 views
1

Je développe un schéma en utilisant RELAX NG. Je suis assez nouveau à ce sujet, donc il est tout à fait possible que je néglige quelque chose d'évident, mais il ne semble pas y avoir un moyen pratique de spécifier le nombre d'occurrences d'un élément comme vous pouvez dans le langage XML Schema. Par exemple, supposons que je veuille spécifier qu'un élément A peut contenir 2 à 5 éléments BComment spécifier une plage numérique d'occurrences dans RELAX NG?

Je ne veux pas utiliser les étiquettes zeroOrMore ou oneOrMore parce que j'ai effectivement une limite supérieure sur le nombre d'éléments. Dans le schéma XML, je peux utiliser les propriétés minOccurs et maxOccurs pour spécifier cela de manière compacte. J'ai lu le official RELAX NG tutorial, écrémé the spec, et fait quelques recherches de base, mais je n'ai pas été en mesure de trouver un moyen pratique de le faire avec RELAX NG. Le mieux que je peux comprendre, vous devez faire quelque chose comme ceci:

<element name="A"> 
    <ref name="B"/> 
    <ref name="B"/> 
    <optional><ref name="B"/></optional> 
    <optional><ref name="B"/></optional> 
    <optional><ref name="B"/></optional> 
</element> 

<define name="B"> 
    <element name="B"> 
    <text/> 
    </element> 
</define> 

Ceci est faisable, mais commencer à regarder laid quand vous avez besoin d'un plus grand nombre d'occurrences. Dans mon schéma actuel, j'ai un type d'élément qui pourrait se produire jusqu'à 256 fois, donc les éléments facultatifs spécifiés manuellement seront clunky. Je le ferai si j'en ai besoin, mais j'aimerais savoir s'il existe une façon plus élégante d'exprimer mes restrictions d'occurrence.

Répondre

3

Il n'y a vraiment pas de façon très maladroite de le faire dans RELAX NG j'ai peur.

Je prendrais l'une des deux approches. Soit construire des modèles ou utiliser les annotations Schematron et processus dans un environnement où vous pouvez faire processus en utilisant les deux langues:

Par exemple, la construction de groupes d'éléments B:

<define name="B2"> 
    <ref name="B"/> 
    <optional><ref name="B"/></optional> 
</define> 

<define name="B4"> 
    <ref name="B2"/> 
    <ref name="B2"/> 
</define> 

vous permettant de construire lentement groupes de (dans ce cas), un ou deux éléments, puis 2-4 éléments et ainsi de suite. Combiner différents groupes vous permettra de spécifier le nombre approprié (éventuellement).

Sinon, vous pouvez utiliser les annotations Schematron:

<?xml version="1.0" encoding="utf-8"?> 
<grammar xmlns="http://relaxng.org/ns/structure/1.0" 
    xmlns:s="http://www.ascc.net/xml/schematron"> 

    <element name="A"> 
     <s:rule context="A"> 
     <!-- note - using XPath 2 here --> 
     <s:assert test='count(B) lt 6'>A elements may contain no more than 6 B elements</s:assert> 
     </s:rule> 
     <ref name="B"/> 
     <oneOrMore><ref name="B"/></oneOrMore> 
    </element> 

    <define name="B"> 
     <element name="B"> 
     <text/> 
     </element> 
    </define> 

</grammar> 

J'ont tendance à préférer ce dernier comme il fait des schémas beaucoup plus simple et il est pas difficile de mélanger les deux, mais cela dépend de votre environnement de validation.

+0

Merci pour les suggestions! J'avais pensé à votre première approche, mais j'ai décidé contre. La deuxième approche semble que ce ne serait pas trop de problèmes. Je finirai probablement par l'utiliser. –