我有一个类似于以下的文档类型: foo settings !-- Must be present; in any order -- timeabc/time validRuntrue/validRun !-- Tool may add whatever ones it wants -- somethingNotCheckedForabc/somethingNotCheckedFor /settings/foo 以下
<foo> <settings> <!-- Must be present; in any order --> <time>abc</time> <validRun>true</validRun> <!-- Tool may add whatever ones it wants --> <somethingNotCheckedFor>abc</somethingNotCheckedFor> </settings> </foo>
以下文档在语义上与前面的文档相同:
<foo> <settings> <validRun>true</validRun> <somethingNotCheckedFor>abc</somethingNotCheckedFor> <time>abc</time> </settings> </foo>
但以下内容无效:
<foo> <settings> <validRun>true</validRun> <somethingNotCheckedFor>abc</somethingNotCheckedFor> <!-- Error: Required element "time" not present --> </settings> </foo>
我尝试了类似下面的内容,但这不起作用,因为< xs:all>不允许包含< xs:any>:
<xs:all> <xs:element name="time" /> <xs:element name="validRun" /> <xs:any /> </xs:all>
在W3C Schema中有没有办法做到这一点?
>您可以使用XSD 1.1,它允许通配符显示在所有组中.>如果您所需的元素位于命名空间中,并且您可以要求生成器添加的元素不在该命名空间中,那么您可以使用可识别所需语言的选项和序列来编写内容模型(如果您确实只需要两个元素,它不是太难;如果你有三个或四个它变得很麻烦,如果你有五个以上,你不想在没有编译器的情况下这样做).你需要的是这样的内容模型:
<xs:sequence> <xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"/> <xs:choice> <xs:sequence> <xs:element ref="time"/> <xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"/> <xs:element ref="validRun"/> </xs:sequence> <xs:sequence> <xs:element ref="validRun"/> <xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"/> <xs:element ref="time"/> </xs:sequence> </xs:choice> <xs:any namespace="##other" minOccurs="0" maxOccurs="unbounded"/> </xs:sequence>
>您可以使用仅包含松散重复通配符的内容模型声明设置,并在应用程序级别(1)检查它是否包含time和validRun以及(2)这两个子项是否有效.
其中,如果您可以使用XSD 1.1验证器,我认为XSD 1.1可能会产生最满意的结果.目前,Xerces J和Saxon-EE都支持XSD 1.1;大多数其他XSD工具没有.