2010-10-24 96 views
56

我有一个正则表达式,我认为工作正常,直到现在。我需要匹配一个可选角色。它可能在那里,也可能不在。正则表达式如何匹配一个可选字符

这里有两个字符串。顶部的字符串是匹配的,而下部的则不匹配。在较低的字符串中没有单个字母是导致它失败的原因。

我想在开始的5位数字之后得到单个字母,如果不存在,则继续获取字符串的其余部分。这封信可以是A-Z

如果我从正则表达式中删除([A-Z]{1}) +.*? +,它将匹配除信件外所需的所有内容,但它很重要。

20000  K    Q511195DREWBT   E00078748521 
30000      K601220PLOPOH   Z00054878524 

这是我正在使用的正则表达式。

/^([0-9]{5})+.*? ([A-Z]{1}) +.*? +([A-Z]{1})([0-9]{3})([0-9]{3})([A-Z]{3})([A-Z]{3}) +([A-Z])[0-9]{3}([0-9]{4})([0-9]{2})([0-9]{2})/ 

回答

112

使用

[A-Z]? 

,使信可选。 {1}是多余的。 (当然,你也可以写[A-Z]{0,1}这意味着相同的,但是这是?是有什么。)

你可以提高你的正则表达式来

^([0-9]{5})+\s+([A-Z]?)\s+([A-Z])([0-9]{3})([0-9]{3})([A-Z]{3})([A-Z]{3})\s+([A-Z])[0-9]{3}([0-9]{4})([0-9]{2})([0-9]{2}) 

而且,因为在大多数的正则表达式方言,\d相同[0-9]

^(\d{5})+\s+([A-Z]?)\s+([A-Z])(\d{3})(\d{3})([A-Z]{3})([A-Z]{3})\s+([A-Z])\d{3}(\d{4})(\d{2})(\d{2}) 

但是:你真的需要11个独立的捕获组?如果是这样,为什么不捕获倒数第四组数字?

+0

Tim,我真的不确定,因为我没有写这个正则表达式。对于正则表达式我还是很新的。如果你看到更好的写作方式,我愿意接受建议。 – jim 2010-10-24 06:45:37

+0

蒂姆,你的例子适用于两个字符串,不管我在那个位置是否有一个字母。谢谢。 – jim 2010-10-24 07:00:51

13

可以使单个字母可选通过后加入?为:

([A-Z]{1}?) 

的量词{1}是多余的,因此您可以将其删除。

+0

感谢codeaddict。问号代替了“+。*”吗? +'? – jim 2010-10-24 06:43:57

+0

使用grep正则表达式时,如果放弃{1}(grep:lookbehind断言不是固定长度),将会出现错误。所以这是一个让它进入的情况。 – Zunderscore 2017-07-26 09:35:04

3

你必须标记单个字母为可选太:

([A-Z]{1})? +.*? + 

或使整个部分可选

(([A-Z]{1}) +.*? +)? 
+0

Stefan,我想让这封信完全可选。我尝试了这两个,但它仍然没有匹配。我确信我错了。你可以修改你的例子,将它包含到字符串中吗? – jim 2010-10-24 06:51:23