用于查找“真实”3位数序列的正则表达式(忽略嵌入4位数序列的序列)

时间:2011-10-10 11:13:03

标签: regex

我想要一个正则表达式(使用Java)捕获三个数字,如“876”,但不是如果它们被埋在一个4位数字序列中。

在“876”和“foo876”,“876”,“876”,“food876”和“4foo876”中捕获“876”。

但不在“88foo9876”或“9876”或“a8876”或“a8876foo”内。

我该怎么做?

我想说一些类似 X(\ d \ d \ d)X 的内容,但代替第一个X来说“ \ D 或< em> ^ (start-string)“并代替第二个X来说” \ D $ (end-string)“。

编辑:

要获得答案,请参阅Xanatos,Code Jockey和Tim Pietzcker。

6 个答案:

答案 0 :(得分:5)

编辑:根据澄清的规格更新:

(?<!\d)\d{3}(?!\d)

<强>解释

(?<!\d) # Assert that there is no digit before the current position
\d{3}   # Match exactly three digits
(?!\d)  # Assert that there is no digit after the current position

(保存初始版本用于存档目的:))

^\D*\d{3}$

如果我理解正确的话。

<强>解释

^     # start of string
\D*   # zero or more non-digits
\d{3} # exactly 3 digits
$     # end of string

答案 1 :(得分:5)

那么,好吧!对于你想要的X(\ d \ d \ d)X,请使用

(?<=\D|^)(\d\d\d)(?=\D|$)

(?<=\D|^)      # lookbehind for «\D or ^ (start-string)»
(\d\d\d)       # then match «three digits such as "876"»
(?=\D|$)       # lookahead for «\D or $ (end-string)»

并将

  

...在“876”,“foo876”,“876”,“876”和“food876”中捕获“876”。

     

但不在“88foo9876”或“9876”或“a8876”或“a8876foo”内。

如你所指定:D

以下显示在RegexBuddy中:

Screenshot of RegexBuddy showing .Net regex emulation

如果您使用的语言没有后顾之忧(如ECMA / JavaScript),则必须使用

(\D|^)(\d\d\d)(?=\D|$)     # and use the second capturing group -or-
                           # use
(?:\D|^)(\d\d\d)(?=\D|$)   # and use the first capturing group

答案 2 :(得分:2)

(?<!\d)(\d{3})(?!\d)

在此测试:http://gskinner.com/RegExr/?2utct

使用零宽度捕获组。表示3位数字前面没有数字,后面没有数字。捕获的唯一东西是3位数。

请注意,如果您使用的是.NET,而不是\d,则应使用[0-9]来捕获09E6 0 BENGALI DIGIT ZERO(0是您的数字:-))

答案 3 :(得分:2)

^\D*\d{3}$

上述工作但您的要求有点模糊。非数字意味着字面上的非数字,因此其他所有内容都允许使用空格。

答案 4 :(得分:0)

我假设您真正想要的是一个正则表达式,它匹配许多编程语言定义的合法变量名称。假设您在开头至少有一个非数字的字符串之后,那么任何东西:那将是/^\D+.*/(您的里程可能会有所不同,具体取决于编程语言)。当然,如果我的假设正确,\D实际上根本不是你想要的东西;你宁愿想要一个可以合法地开始变量的字符列表(粗略地,字母字符,加上下划线,可能还有一些其他字符)。因此,这更像是/[A-Za-z_]+.*/

但正如已经说过的那样,你真的需要更加具体。

答案 5 :(得分:0)

这是一个正则表达式,它将匹配3个数字的序列,而不是在另一个数字之前或之后。

[^\d](\d{3})[^\d]/

插入符号(^)否定了字符类,这意味着它匹配除数字之外的任何内容。 {3}指定中间数字序列中需要多少位数。

编辑,抱歉我没有在序列开始的单个字符串上测试它和/或以我们想要的序列中的数字结束。这应该解决这个问题,获得一些额外的捕获,但是你可以忽略那些。修正了,因为我太过完美主义了

(?:^|[^\d])(\d{3})(?:[^\d]|$)

部分更多解释。

(?:^|[^\d]); ?:使得组((括号之间的所有内容)都不会被捕获。 ^|[^\d]表示字符串的开头或任何不是数字的内容。

(\d{3});捕获正好3位数的组

(?:[^\d]|$);基本上和开头一样,但后面跟一个字符串的结尾或任何不是数字的东西......