使用 Javascript 中的正则表达式验证 xs:duration

Validate a xs:duration using a regular expression in Javascript

我正在尝试验证 xs:duration,然后将其转换为秒。此时,这是我拥有的:

/P^([-])?(([\d.]*)Y)?(([\d.]*)M)?(([\d.]*)D)?T?(([\d.]*)H)?(([\d.]*)M)?(([\d.]*)S)?/

但是,不拒绝这些无效值(取自 here):

我错过了什么?

我发现了一个类似的问题 here,但该正则表达式仅适用于 Python。

您遗漏了几点,通过查看失败案例的描述很容易解决。以下正则表达式适用于所有情况(和失败情况),请参阅 Regex 101

^(-?)P(?=.)((\d+)Y)?((\d+)M)?((\d+)D)?(T(?=.)((\d+)H)?((\d+)M)?(\d*(\.\d+)?S)?)?$

首先来看P15.5Y only the seconds can be expressed as a decimal。您在任何地方都使用 [\d.]*,这样就可以在任何地方使用一个或多个数字或点。但是只允许秒有一个点,并且该点后面需要跟一个数字。因此,将秒数更改为 (\d*(\.\d+)?S),将所有其他秒数更改为 (\d+Y)(依此类推)。

此外,字符串需要以可选的 - 开头,然后是 P,因此请使用:

^-?P

然后,P 之后一定有东西,只需为此使用先行断言:

(?=.)

然后,出现 YMD,如前所述。

如果有时间成分,现在肯定有 T,所以确保我们有 T,如果有其他情况:

(T(?=.))

...并且只有当我们有一个 T 时,我们才可以有 HMS:

(T(?=.)(\d+H)?(\d+M)?(\d*(\.\d+)?S)?)

先行断言确保我们会找到一些东西,其余的捕获 HMS 部分。