尝试从最后两行进行匹配,返回的信息太多
我想仅仅针对多行地址中的最后两行(斜体标注部分)进行匹配,并返回这两行末尾的任意一个五位数字,忽略上面几行中的五位数字。目前它会匹配到数字,但结果把前一行也包含进去了。
当前模式:
"(?:.*\n)?(\d{5})$"
示例文本:
Bob Smith
123 Maple St Apt 44456
44325 Blue Building
Newington, CT. 06000
06111
应该从第4、5行中匹配出06111和 06000。
解决方案
Update: Simplified Regex
我会使用以下正则表达式:
\b\d{5}(?=$|\n.*$)
请参见 Regex Demo
\b确保任何五位数字字符串在单词边界处开始。正则中的前瞻断言(下文描述)确保该五位数字字符串在单词边界处结束。如果你想在字符串 '1234567' 中匹配 '34567',可以移除\b。\d{5}匹配一个五位数字。(?=$|\n.*$)是一个前瞻断言,表示正在匹配的五位数字后面要么是字符串结束,要么是一行结束后紧接着一个额外但可能为空的字符串。因此,我们只会匹配出现在行末的五位数字,但仅限于最后两行。
过时的原始建议
请注意,下面是一条在步骤数上都很昂贵的正则,即使对你的简单输入也是如此。你不如改用非正则的方法先获取输入的最后两行,然后再使用 \d{5} 作为正则表达式。
你可以使用 Regex.Matches 方法配合以下正则,返回最后两行中找到的所有五位数字:
(?=(?:.*\n)?.*\n?$)\d{5}(?=\n|$)
(?=(?:.*\n)?.*\n?$)- 这是一个前瞻断言,表示后面跟着的是最后两行或最后一行,且最后一行可能以换行符结束也可能不结束。\d{5}(?=\n|$)匹配在行尾或字符串结束之前的5个连续数字(以防最后一行没有以换行符结束)。
前瞻断言的工作原理如下:
(?:.*\n)? 是一个可选的以换行符结束的行,除了换行符外可以为空。
.*\n?$ 匹配最后一行,可能为空,且可选地以换行符结束。
因此,这个前瞻断言将匹配到五位数字,即使输入只有一行,且它可能以换行符结束也可能不结束。
请参见 regex demo
你还可以把正则写成如下形式:
(?=(?:.*\n)?.*\n?$)\b\d{5}\b(?=\n|$)
这样你的正则就能确保所匹配的五位数字处在单词边界上。也就是说,例如不会匹配到 '1234567' 的任意部分。第二个 \b 实际上并非必需,可以省略,因为我们使用了前瞻断言,确保五位数字后面跟着换行符或字符串结束,这也意味着五位数字的末尾处于单词边界。
如果你确定输入的最后两行每一行都至少有一个五位数字,如你提供的示例文本那样,你也可以只匹配输入中的所有五位数字,然后只考虑最后两行。这比使用前瞻断言来确保只在最后两行匹配五位数字更高效。或者,如果最后两行中的任一行或两行可能出现多个五位数字,你也可以用 Regex.Split 将输入的最后两行isolating出来,然后对每一行匹配 \d{5}$。