JavaRush /Java 博客 /Random-ZH /RegEx:掌握正则表达式的 20 个简短步骤。第1部分
Artur
第 40 级
Tallinn

RegEx:掌握正则表达式的 20 个简短步骤。第1部分

已在 Random-ZH 群组中发布
这篇文章的原文在这里。也许没有太多的理论,我将在文章末尾提供一些关于正则表达式的更详细材料的链接。但在我看来,如果有机会不仅可以临时抱佛脚,而且还可以通过完成小任务来立即巩固知识,那么开始钻研正则表达式这样的主题会更有趣。 RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 1 部分让我们开始吧。通常,反对在编程中使用正则表达式(“RegEx”或简称“regex”)的人会引用 Jamie Zawinski 的以下引言: “有些人在遇到问题时会想,‘我知道,我会使用正则表达式”“现在他们有两个问题”。 事实上,使用正则表达式还没有好坏之分。这本身不会增加问题,也不会解决任何问题。它只是一个工具。你如何使用它(正确或错误)决定了你会看到什么结果。例如,如果您尝试使用正则表达式来创建 HTML 解析器,那么您很可能会遇到痛苦。但是,如果您只想从某些字符串中提取时间戳,那么您可能会没问题。为了让您更轻松地掌握正则表达式,我整理了本课程,只需二十个简短的步骤即可帮助您从头开始掌握正则表达式。本教程主要关注正则表达式的基本概念,并仅在必要时深入研究更高级的主题。

第 1 步:为什么使用正则表达式

RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 2 部分正则表达式用于使用指定的模式(pattern)在文本中搜索匹配项。使用正则表达式,我们可以轻松简单地从文本中提取单词,以及满足特定条件的单个文字和元字符及其序列。以下是维基百科 对它们的介绍:正则表达式是一种基于元字符(通配符)的使用来搜索和操作文本中子字符串的正式语言。对于搜索,使用示例字符串(英语模式,在俄语中通常称为“模板”、“掩码”),由符号和元符号组成并定义搜索规则。为了操作文本,还指定了替换字符串,该字符串也可以包含特殊字符。 该模式可以像dog这句话中的单词一样简单:
敏捷的棕色狐狸跳过了懒狗。
这个正则表达式看起来像这样:
...很容易,不是吗?该模式也可以是包含该字母的任何单词o。查找此类模式的正则表达式可能如下所示:
\哇* _
您可以在这里尝试这个正则表达式。)您会注意到,随着“匹配”要求变得更加复杂,正则表达式也变得更加复杂。还有其他形式的符号用于指定字符组和匹配重复模式,我将在下面解释。但是,一旦我们在某些文本中找到与模式的匹配,那么我们可以用它做什么呢?现代正则表达式引擎允许您从包含的文本中提取字符或字符序列(子字符串),或将其删除,或将其替换为其他文本。一般来说,正则表达式用于解析和操作文本。例如,我们可以提取看起来像 IP 地址的子字符串,然后尝试验证它们。或者我们可以提取姓名和电子邮件地址并将它们存储在数据库中。或者使用正则表达式查找电子邮件中的敏感信息(例如护照号码或电话号码),并提醒用户可能会将自己置于危险之中。正则表达式确实是一种易于学习但难以掌握的多功能工具: “正如演奏好一首音乐和创作音乐之间存在差异一样,了解正则表达式和理解它们之间也存在差异。” - Jeffrey E. F. Friedl,《掌握正则表达式》

第 2 步:方括号[]

最容易理解的最简单的正则表达式是那些简单地在正则表达式模式和目标字符串之间查找逐字符匹配的正则表达式。例如,让我们尝试寻找一只猫: RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 3 部分
图案:
字符串:猫跑到车底下时被割伤。
匹配:      ^^^
它在实践中是如何运作的 - 请参阅此处注意! 此处提供的所有解决方案仅作为可能的解决方案。在正则表达式中,就像在一般编程中一样,您可以用不同的方式解决相同的问题。 然而,除了严格的逐个字符比较之外,我们还可以使用方括号指定替代匹配:
模式:ca[rt]
字符串:猫跑到车底下时被割伤。
匹配:      ^^^ ^^^
它是如何工作的)左方括号和右方括号告诉正则表达式引擎它应该匹配任何指定的字符,但只能匹配一个。例如,上面的正则表达式不会找到cart整个单词,而只会找到其中的一部分:
模式:ca[rt]
字符串:猫跑到车底下时被割伤。
匹配:      ^^^ ^^^
它是如何工作的)当您使用方括号时,您告诉正则表达式引擎仅匹配方括号内包含的字符之一。引擎先找到字符c,然后找到字符a,但如果下一个字符不是rt,则这不是完全匹配。如果它找到ca,然后是r,或者t,它就会停止。它不会尝试匹配更多字符,因为方括号表示只需要匹配所包含的字符之一。当它找到时ca,它会r在单词next 中查找cart,然后停止,因为它已经找到了该序列的匹配项car

培训目标:

编写一个正则表达式,与这段不可翻译的当地方言双关语摘录 had中的所有 10 个模式相匹配:Had
图案:
字符串:Jim,其中 Bill 有“had”,有“had had”“曾经”是正确的。
匹配:                  ^^^ ^^^ ^^^ ^^^ ^^^ ^^^ ^^^ ^^^ ^^^ ^^^
请参阅此处可能的解决方案)以下句子中的所有动物名称怎么样?
图案:
字符串:一只蝙蝠、一只猫一只老鼠走进了一家酒吧……
匹配:    ^^^ ^^^ ^^^
可能的解决方案)或者更简单:找到单词baror bat
图案:
字符串:一只蝙蝠、一只猫一只老鼠走进了一家酒吧……
匹配:    ^^^ ^^^
可能的解决方案)现在我们已经学会了如何编写或多或少复杂的正则表达式,并且我们仅处于第2步!让我们继续吧!

第 3 步:转义序列

RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 4 部分在上一步中,我们了解了方括号[]以及它们如何帮助我们使用正则表达式引擎找到替代匹配项。但是,如果我们想查找左方括号和右方括号本身形式的匹配项怎么办[]?当我们想要查找单词 的逐个字符匹配时cat,我们向正则表达式引擎提供了这个字符序列 ( cat)。[]让我们尝试以同样的方式 找到方括号:
模式:[]
字符串:你不能使用正则表达式匹配[]!你会后悔的!
火柴: 
让我们看看发生了什么)但是,有些东西不起作用...这是因为方括号字符充当特殊的正则表达式引擎字符,通常用于指示其他内容,而不是匹配它们本身的文字模式。正如我们在步骤 2 中所记得的那样,它们用于查找替代匹配项,以便正则表达式引擎可以匹配它们之间包含的任何字符。如果它们之间不放置任何字符,则可能会导致错误。为了匹配这些特殊字符,我们必须在它们前面加上反斜杠字符来转义它们\。反斜杠(或反斜杠)是另一个特殊字符,它告诉正则表达式引擎按字面意思查找下一个字符,而不是将其用作元字符。正则表达式引擎只会查找字符[]字面意思,如果它们前面都有反斜杠:
图案:\[\]
字符串:您无法使用正则表达式匹配 []!你会后悔的!
匹配:                  ^^ 
让我们看看这次发生了什么)好吧,如果我们想找到反斜杠本身怎么办?答案很简单。由于反斜杠\也是特殊字符,因此也需要转义。如何?反斜杠!
图案:\\
字符串:C:\Users\Tanja\Pictures\Dogs
匹配:    ^ ^ ^ ^
实践中的相同示例)只有特殊字符前面才应该有反斜杠。默认情况下,所有其他字符均按字面解释。例如,正则表达式t仅匹配t小写字母:
图案: t
字符串:tttt
匹配:^ ^ ^ ^
示例)但是,此序列的\t工作方式有所不同。这是一个用于搜索制表符的模板:
模式:\t
字符串:tttt
匹配:   ^ ^ ^
示例)一些常见的转义序列包括\n(UNIX 样式换行符)和\r(用于 Windows 样式换行符\r\n)。\r是“回车”字符和\n“换行”字符,这两个字符都是在电传打字机仍在广泛使用时与 ASCII 标准一起定义的。 本教程稍后将介绍其他常见的转义序列。

与此同时,让我们用几个简单的谜题来强化材料:

尝试编写正则表达式来查找...正则表达式;)结果应该是这样的:
图案:
字符串:...将此正则表达式 ` \[\] ` 与正则表达式匹配?
匹配:                       ^^^^	
解答)你做到了吗?做得好!现在尝试创建一个正则表达式来搜索转义序列,如下所示:
图案:
字符串:` \r `、` \t ` 和 ` \n ` 都是正则表达式转义序列。
匹配:   ^^ ^^ ^^
解决方案

第 4 步:使用点查找“任意”字符.

RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 5 部分在编写我们在上一步中看到的转义序列匹配解决方案时,您可能想知道,“我可以匹配反斜杠字符,然后匹配它后面的任何其他字符吗?”...当然可以!还有另一个特殊字符用于匹配(几乎)任何字符 - 点(句号)字符。它的作用如下:
图案:
string:对不起,戴夫。恐怕我做不到。
匹配:^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^	
示例)如果您只想匹配看起来像转义序列的模式,您可以执行以下操作:
图案:\\。
字符串:嗨,沃尔玛是我的孙子,他的名字是“ \n\r\t ”。
匹配:                                             ^^ ^^ ^^	
示例)并且,与所有特殊字符一样,如果要匹配文字.,则需要在其前面添加一个字符\
图案:\。
字符串:战争即和平自由就是奴役无知就是力量
匹配:            ^ ^ ^
例子

第 5 步:字符范围

RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 6 部分如果您不需要任何符号,而只想在文本中查找字母怎么办?还是数字?还是元音?按字符类别及其范围进行搜索将使我们能够实现这一目标。
` \n `、` \r ` 和 ` \t `空白字符,` \。`、` \\ ` 和 ` \[ `不是
如果字符不在文本中创建可见标记,则它们 是“空白” 。 空格“ ”是空格、换行符或制表符。假设我们想要找到仅代表上面段落中的空白字符 和 的转义序列,而不是其他转义\n序列\r\t我们怎样才能做到这一点?
模式:\\[nrt]
字符串:` \n `、` \r ` 和 ` \t `空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:   ^^ ^^ ^^	
示例)这可行,但不是一个非常优雅的解决方案。如果稍后我们需要匹配“换页”字符的转义序列怎么办\f?(此符号用于指示文本中的分页符。)
模式:\\[nrt]
字符串:` \n`、` \r`、` \t`和 ` \f`空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:   ^^ ^^ ^^	
不起作用的解决方案)使用这种方法,我们需要在方括号中单独列出我们想要匹配的每个小写字母。一种更简单的方法是使用字符范围来匹配任何小写字母:
模式:\\[az]字符串
:` \n`、` \r`、` \t`和 ` \f`空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:   ^^ ^^ ^^ ^^	
这已经有效)考虑到上面的示例,字符范围正如您所期望的那样工作。将要匹配的第一个和最后一个字母放在方括号内,中间使用连字符。例如,如果您只想查找反斜杠\ato中的一个字母的“组” m,您可以执行以下操作:
模式:\\[am]字符串
:` \n`、` \r`、` \t`和 ` \f`空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:                         ^^	
示例)如果要匹配多个范围,只需将它们首尾相连地放在方括号之间:
模式:\\[a-gq-z]
字符串:` \n `、` \r `、` \t ` 和 ` \f `空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:         ^^ ^^ ^^	
示例)其他常见字符范围包括:A-Z0-9

让我们在实践中尝试一下并解决几个问题:

十六进制数字可以包含数字0-9和字母A-F。当用于指定颜色时,十六进制代码最多可以包含三个字符。创建正则表达式以在下面的列表中查找有效的十六进制代码:
图案:
字符串:1H8 4E2 8FF 0P1 T8B 776 42B G12
匹配:      ^^^ ^^^ ^^^ ^^^	
解决方案)使用字符范围,创建一个正则表达式,该表达式将仅选择y下面句子中的小写辅音(不是元音,包括 ):
图案:
字符串:商场非常 _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 
匹配:   ^ ^ ^^^ ^ ^^ ^ ^^ ^ ^ ^ ^^^ ^ ^ ^^^ ^ ^^	
解决方案

第 6 步:“not”、脱字号、抑扬符、脱字号...符号^

RegEx:掌握正则表达式的 20 个简短步骤。 第 1 - 7 部分确实,这个符号有超过 9000 个名称:)但是,为了简单起见,也许我们会关注“not”。我对最后一个问题的解决方案有点长。“获取除元音之外的整个字母表”需要 17 个字符。当然,还有一种更简单的方法可以做到这一点。“not”符号^允许我们指定不能模式中指定的字符和字符范围匹配的字符和字符范围。上面最后一个问题的一个更简单的解决方案是查找不代表元音的字符:
模式:[ ^ aeiou ]字符串
:  商场里非常_ _ _ _ _ _ _ _ _ _ _ _ _ _ 
匹配:^^ ^^ ^^^^ ^^^^ ^^ ^^^ ^ ^^ ^ ^^^^^^ ^ ^^^^^ ^^^ 	
示例)“not”符号^作为方括号内最左边的字符,[]告诉正则表达式引擎匹配不在方括号内的一个(任何)字符。这意味着上面的正则表达式还匹配句子开头的所有空格、句号.、逗号,和大写字母。T为了排除它们,我们还可以将它们放在方括号中:
模式[ ^ aeiou . , T ]字符串 
:房间非常_ _ _ _ _ _ _ _ _ _ _ _ _ _ 
匹配:   ^ ^ ^^^ ^ ^^ ^ ^^ ^ ^ ^ ^^^ ^ ^ ^^^ ^ ^^	
例子笔记在这种情况下,我们不需要用反斜杠来转义句点,就像我们之前在不使用方括号查找它时所做的那样。方括号中的许多特殊字符按字面意思处理,包括左括号字符[,但不包括右括号]字符(你能猜出为什么吗?)。反斜杠字符\也不按字面解释。如果要\使用方括号匹配文字反斜杠,则必须通过在其前面添加以下反斜杠对其进行转义\\。此行为的设计是为了使空白字符也可以放置在方括号中进行匹配:
模式:[\t]
字符串:tttt
匹配:   ^ ^ ^
示例)“not”符号^也可以与范围一起使用。如果我只想捕获字符a, b, c, x,yz,我可以这样做:
模式:[abcxyz]
字符串:   abc defghijklmnopqrstuvw xyz
匹配:^^^ ^^^
示例)...或者,我可以指定我想要查找不在d之间的任何字符w
模式:[^dw]
字符串:   abc defghijklmnopqrstuvw xyz
匹配:^^^ ^^^
示例)但是,当心与“不” ^。人们很容易想到“好吧,我指定了[^ b-f],所以我应该在 后得到一个小写字母a或其他东西f。事实并非如此。这个正则表达式将匹配不在该范围内的任何字符,包括字母、数字、标点符号和空格。
模式:[^dw]
字符串:   abc defg h i , j - klmnopqrstuvw xyz
匹配:^^^ ^ ^ ^ ^ ^^^
例子

升级任务:

使用方括号中的“not”符号^来匹配下面所有不以 结尾的单词y
图案:
字符串:daydog hog hay bog bay ray rub
匹配:      ^^^ ^^^ ^^^ ^^^	
解决方案)使用范围和“非”符号编写正则表达式^来查找 1977 年到 1982 年(含)之间的所有年份:
图案:
字符串:1975 1976 1977 1978 1979 1980 1981 1982 1983 1984
匹配:            ^^^^ ^^^^ ^^^^ ^^^^ ^^^^ ^^^^
解决方案)编写一个正则表达式来查找所有不是“not”符号字符的字符^
图案:
字符串:   abc1 ^ 23*()
匹配:^^^^ ^^^^^	
解决方案

第 7 步:字符类

字符类甚至比字符范围更简单。不同的正则表达式引擎有不同的可用类,因此我在这里只介绍主要的类。(检查您正在使用哪个版本的正则表达式,因为可能有更多版本 - 或者它们可能与此处显示的不同。)字符类的工作方式几乎与范围类似,但您无法指定“开始”和“结束”值:
班级 符号
\d “数字”[0-9]
\w “文字符号”[A-Za-z0-9_]
\s “空间”[ \t\r\n\f]
“word”字符类\w特别有用,因为各种编程语言中的有效标识符(变量名称、函数名称等)通常需要此字符集。我们可以用它\w来简化我们之前看到的正则表达式:
模式:\\[az]字符串
:` \n`、` \r`、` \t`和 ` \f`空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:   ^^ ^^ ^^ ^^	
使用\w我们可以这样写:
模式:\\\w
字符串:` \n`、` \r`、` \t`和 ` \f`是空白字符,` \. `、` \\ ` 和 ` \[ `不是。
匹配:   ^^ ^^ ^^ ^^	
例子

2个幸运任务:

正如你我所知,在 Java 中,标识符(变量、类、函数等的名称)只能以字母a- zA- Z、美元符号$或下划线开头_。(下划线当然是不好的风格,但编译器会跳过它,译者注)。其余字符必须是“word”字符\w。使用一个或多个字符类,创建正则表达式以在以下三字符序列中搜索有效的 Java 标识符:
图案:
字符串:   __e $12 .x2 foo Bar 3mm
匹配:^^^ ^^^ ^^^ ^^^	
(解决方案) 美国社会安全号码 (SSN) 是 9 位数字,格式为 XXX-XX-XXXX,其中每个 X 可以是任意数字[0-9]。使用一个或多个字符类,编写正则表达式以在下面的列表中查找格式正确的 SSN:
图案:
字符串:113-25=1902 182-82-0192 H23-_3-9982 1I1-O0-E38B
匹配:              ^^^^^^^^^^^
解决方案RegEx:20个简短步骤掌握正则表达式。第 2 部分: 掌握正则表达式的 20 个简短步骤。第 3 部分 :正则表达式:掌握正则表达式的 20 个简短步骤。第 4 部分。
评论
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION