我希望只有在前面的正则表达式匹配的情况下才需要一些字符。如果不是,则不需要任何字符(空字符串(。例如,如果在前四个字符之后出现组(A10、B32、C56、D65(中的一个字符串(枚举类型(_"然后是一个3位数的数字,如123。如果没有出现上述组中的任何元素,则不需要其他字符串。我的第一次尝试是这样的,但ELSE分支不起作用:
^XXX_(?<DT>A12|B43|D14)(?(DT)(_d{1,3})|).ZZZ$
- XXX_A12_123.ZZZ->匹配
- XXX_A11.ZZZ->匹配
- XXX_A12_abc.ZZZ->没有匹配
- XXX_A23_123.ZZZ->没有匹配
这些是文件名的示例。如果文件名包含一个上述组的字符串,如A12或C56,那么我希望这个元素后面跟着一个下划线,后面跟着1到3位数字。如果文件名不包含该组的字符串(没有字符或与组中的字符串不同的字符序列(,那么我不希望看到后面跟着1到3位数字的下划线。
例如,我可以将正则表达式扩展到
^XXX_(?<DT>A12|B43|D14)_d{5}(?(DT)(_d{1,3})|)_someMoreChars.ZZZ$
然后我希望这些文件名是有效的:
- XXX_A12_12345_123_wellDone.ZZZ
- XXX_Q21_00000_wellDone.ZZZ
- XXX_Q21_00000_456-wellDone.ZZZ
。。。但这是无效的:
- XXX_A12_12345_wellDone.ZZZ
如何使条件语句的ELSE分支工作?
最后,我打算有两个小组A组:(A11、B32、D76、R33(B组:(A23、C56、H78、T99(
如果组A的一个元素出现在文件名中,那么我希望在该文件名中找到_\d{1,3}。如果组B的元素出现在文件名中,则_\d{1,3}应是可选的(它可能出现在文件中,也可能不出现(。
我最终得到了这个正则表达式:
^XXX_(?:(?<DT>A12|B43|D14))?_d{5}(?(DT)(_d{1,3})|(?!(?&DT))(?!.*_d{3}(?!d))).+.ZZZ$
由于我必须在OpenApi@Pattern注释中使用这个正则表达式,我遇到了错误:
此regex方言不支持条件。
As@第四只鸟建议的交替似乎奏效了:
XXX_((((A12|B43|D14)_d{5}_d{1,3}))|((?:(A10|B10|C20)((?:_d{5}_d{3})|(?:_d{3}))))).*.ZZZ$
else分支是|
之后的部分,但如果您也想匹配第二个示例,则if子句将不起作用,因为您已经匹配了A12|B43|D14
中的一个
命名捕获组不是可选的,因此if子句将始终为true。
相反,您可以使用交替来匹配后面跟着下划线和3位数字的记数部分,或者匹配大写字符和2位数字。
^XXX_(?:(?<DT>A12|B43|D14)_d{1,3}|[A-Z]d{2}).ZZZ$
Regex演示
如果要使用If/else子句,可以将命名的捕获组设置为可选,然后检查组1是否存在。
^XXX_(?<DT>A12|B43|D14)?(?(DT)_d{1,3}|[A-Z]d{2}).ZZZ$
Regex演示
对于更新的问题:
^XXX_(?<DT>A12|B43|D14)?(?(DT)(?:_d{5})?_d{3}(?!d)|(?!A12|B43|D14|[A-Z]d{2}_d{3}(?!d))).*.ZZZ$
模式匹配:
^
字符串开始XXX_
按字面匹配(?<DT>A12|B43|D14)?
(?(DT)
如果我们有DT组(?:_d{5})?
可选匹配_和5位数字_d{3}(?!d)
匹配_
和3位数字|
或(?!
否定前瞻,断言不向右A12|B43|D14|
匹配其中一个备选方案,或[A-Z]d{2}_d{3}(?!d)
匹配1个字符A-Z,2个数字_3个数字后面没有数字
)
关闭前瞻
)
关闭if子句.*
匹配行的其余部分.ZZZ
匹配.
和ZZZ$
字符串结束
Regex演示