RELAX NG基于其他元素的条件数据类型

时间:2013-01-10 12:02:47

标签: xml relaxng relaxng-compact

我的目标是建立一个RELAX NG紧凑模式,强制元素的数据类型与父元素的数据类型匹配。

我目前有以下架构:

start = Tickmarks

Tickmarks = element tickmarks { 
    attribute from { xsd:float | xsd:date },
    attribute to { xsd:float | xsd:date },
    Tick*
}

Tick = element tick { 
    attribute value { xsd:float | xsd:date },
    attribute label { text }
}

我想要的是描述文档的模式,如果Tickmarks / @来自浮点数,则Tickmarks / Tick / @值也必须是浮点数。

所以基本上它应该满足以下测试:

VALID

<tickmarks from="1" to="10">
  <tick value="3" label="3"/>
  <tick value="7" label="7"/>
</tickmarks>

VALID

<tickmarks from="2000-01-01" to="2006-01-01">
  <tick value="2002-01-01" label="2002"/>
  <tick value="2004-01-01" label="2004"/>
</tickmarks>

INVALID

<tickmarks from="2000-01-01" to="2006-01-01">
  <tick value="10" label="10"/>
  <tick value="20" label="20"/>
</tickmarks>

INVALID

<tickmarks from="1" to="10">
  <tick value="2002-01-01" label="2002"/>
  <tick value="2004-01-01" label="2004"/>
</tickmarks>

RELAX NG compact可以实现吗?

1 个答案:

答案 0 :(得分:3)

如果您想继续使用纯RELAX NG(并避免使用嵌入式Schematron规则等替代解决方案),您可以使用:

start = Tickmarks

Tickmarks = element tickmarks { 
    (
     attribute from { xsd:float },
     attribute to { xsd:float },
     Tick-float*)
    | (
       attribute from { xsd:date },
       attribute to { xsd:date },
       Tick-date*)
}

Tick-float = element tick { 
    attribute value { xsd:float },
    attribute label { text }
}

Tick-date = element tick { 
    attribute value { xsd:date },
    attribute label { text }
}