.NETCore :正则表达式

32 篇文章 2 订阅
18 篇文章 0 订阅

本节内容为正则表达式的使用

简介


有的时候,你是否有过这种需求:判断一个Ip地址、邮箱、密码规则是否合法。如果让你使用if一类的传统方法进行处理,你肯定会被逼疯的。而对于绝大多数的编程语言而言,都有一个字符串处理利器————正则表达式。它可以轻松的让字符串和规则匹配上。有点这样的意思,从前你是判断字符串,去遍历它,而有了正则表达式,你是在书写一个通用性质的规则,让字符串与规则进行匹配。正则表达式本质上就是一串蕴含了一些特殊字符规则的字符串,因此我们书写正则表达式其实是在书写一个字符串,只是它代表了一定的规则而已。

常见的几种正则符号


事实上正则表达式没有过多的知识点,只是一些技巧性的训练,但请相信我,正则表达式是非常重要的。熟练的使用下列的正则符号会对你大有脾益。

元字符
元字符说明
.匹配除了换行符以外的任意字符
\w匹配字母、数字、下划线以及汉字
\s匹配任意空白符
\d匹配数字
\b匹配单词的开始或结束
^匹配字符串的开始
$匹配字符串的结束

1.例如匹配abc开头的字符串

\babc 或者 ^abc

2.匹配5位数字的字符串

^\d\d\d\d\d$
重复限定符号

有了元字符就可以写不少的正则表达式了,但细心的你们可能会发现:别人写的正则简洁明了,如果你只使用元字符进行正则表达式的书写,既不美观也不实用,因此我们使用重复限定符进行重复数据的处理,下面我们来看一些限定符:

字符说明
*重复0次或多次
+重复一次或一次以上
?重复0次或一次
{n}重复n次
{n,}重复n次或更多次
{n,m}重复n到m次

现在我们就能书写相当美观的正则表达式了,例如:
1.匹配7位数字的电话号码

^\d{7}$ 

2.匹配138开头的手机号

^138\d{8}

3.匹配a开头,若干个b结尾的字符串

^ab*$
分组

现在我们已经学会以一点关于书写正则表达式的方法,不过,我们现在无论是匹配还是重复都是针对单个字符进行操作,假如说我希望匹配一个以ab为循环的重复字符串应该如何去处理呢?

答案很简单,就是分组,分组我们通常使用()进行分组,例如匹配以ab为循环的字符串为:

^(ab)*
转义字符

有的时候,我们需要匹配的字符串中本身就含有正则表达式中的关键字符,我们则需要转义,例如我们需要匹配(ab)为循环的字符串:

^(\(ab\))*

反斜杠\就是我们的转义字符。不过对于C#中,字符串含有反斜杠会自动转义,为了避免这种情况,我们需要在字符串之前加上@或者将将转义字符转义,也就是\两个斜杠

条件或

有的时候,我们需要匹配的字符串可能是ab开头也有可能是cd开头,这个时候我们就使用条件语句处理,例如:

^(ab|cd)*

用逻辑或“|”进行处理。

区间匹配

有的时候,我们有可能是需要匹配比如说138-150之间所有数字开头的字符串,或者说A-F按字母表顺序内的字母开头,我们可以这样

^[138-150]*
^[A-F]*
反义

之前我们谈论的都是字符串中含有什么什么,现在我们可能需要匹配到字符串中不含有的字符,那么我们就需要使用反义,如下表

元字符说明
\W匹配不是字母、数字、下划线以及汉字
\S匹配不是空白符
\D匹配不是数字
\B匹配不是单词的开始或结束
[^x]匹配出了x以外的任意字符

贪婪模式与懒惰模式


贪婪

贪婪是当正则表达式中包含能接受重复的限定符时,通常的行为是(在使整个表达式能得到匹配的前提下)匹配尽可能多的字符,这匹配方式叫做贪婪匹配。特性:一次性读入整个字符串进行匹配,每当不匹配就舍弃最右边一个字符,继续匹配,依次匹配和舍弃(这种匹配-舍弃的方式也叫做回溯),直到匹配成功或者把整个字符串舍弃完为止,因此它是一种最大化的数据返回,能多不会少。

事实上我们之前所谈论的重复限定符就是一种贪婪量词
举个例子例如我们需要匹配由2-5个数字组成的字符串,假设有这样一串数字51354 8454 1 568,使用^\d{2,5}进行匹配的结果是51354 8454 568,事实上对于这些而言,匹配两个就已经满足了,例如51已经满足该正则式,但是在贪婪匹配中,它会尽可能的多匹配,将整个字符串输出。

如果多个贪婪量词叠加在一起,如果字符串能满足他们各自最大程度的匹配时,就互不干扰,但如果不能满足时,会根据深度优先原则,也就是从左到右的每一个贪婪量词,优先最大数量的满足,剩余再分配下一个量词匹配。

懒惰

懒惰匹配:当正则表达式中包含能接受重复的限定符时,通常的行为是(在使整个表达式能得到匹配的前提下)匹配尽可能少的字符,这匹配方式叫做懒惰匹配。特性:从左到右,从字符串的最左边开始匹配,每次试图不读入字符匹配,匹配成功,则完成匹配,否则读入一个字符再匹配,依此循环(读入字符、匹配)直到匹配成功或者把字符串的字符匹配完为止。

使用懒惰量词就是在贪婪量词后面中加?,对于之前的例子,他会匹配成51 35 84 54 56

拓展


零宽断言

零宽断言用于查找在某些内容(但并不包括这些内容)之前或之后的东西,也就是说它们像\b,^,$那样用于指定一个位置,这个位置应该满足一定的条件(即断言),因此它们也被称为零宽断言。最好还是拿例子来说明吧: 断言用来声明一个应该为真的事实。正则表达式中只有当断言为真时才会继续进行匹配。

非常抽象而且笼统,对吧,事实上我也那么觉得,以上内容来自百度百科,因为我实在是很难解释这个东西,你可以理解为匹配不含正则结果的内容吧。
正向先行断言(正前瞻)

正前瞻的语法为:

//pattern为正则式
(?=pattern)

它用于匹配pattern表达式之前的内容,并不返回本身。感觉还是很奇怪对吧,举一个例子:今年我市GDP为5600亿元。假设你要将这句话中的5600取出来,你使用正前瞻的方式应该怎么做?

\d+(?=亿元)

正向后行断言(正后顾):

正后顾的语法为:

//pattern为正则式
(?<=pattern)

与正前瞻相反,他是返回pattern之后的内容,如果继续实现之前的内容,那么表达式就会变成

(<=今年我市GDP为)\d+

负向先行断言(负前瞻)

负前瞻的语法为:

//pattern为正则式
(?!pattern)

匹配非pattern表达式的前面内容,不返回本身。还是举之前的例子,我要找到5600亿元之前的字母,那么可以是

[A-Z]+(?!5600亿元)

负向后行断言(负后顾)

这个想必我不需要进行讲解各位也应当能思考出如何书写及使用了,他的语法类似的是:

//pattern为正则式
(?<!pattern)

作用当然是匹配非pattern之后的内容。

我在这里就举这几个例子,还有一些很好的使用手册你可以参考Microsoft Documents。

捕获与非捕获

捕获你可以理解为将表达式按组分配,例如你匹配一个电话010-8511561,010是区号,我们有可能利用正则式将它单独取出来。
数字编号捕获组

语法就是我们之前的分组,但是匹配这个电话号码的时候,他的表达式如果是

((\d{3})-(\d{7}))

那么他会分为三组,第一组是完整的电话,第二组是我们的区号,第三组是我们的电话号码。
命名编号捕获组

语法:

(?<name>exp)

这个name就是你自己自定义的,例如之前的我们可以写成

(?<quhao>\d{3})-(?<haoma>\d{7})

这样我们可以通过名称进行访问组内数据,具体的使用我会在后面进行讲解。
非捕获组

同之前相反,它用于表示不需要分组的数据

(?:exp)

例如我们不需要区号,那么正则式就变成了

(?:\d{3})-(\d{7})

反向引用

捕获会返回一个捕获组,这个分组是保存在内存中,不仅可以在正则表达式外部通过程序进行引用,也可以在正则表达式内部进行引用,这种引用方式就是反向引用。

同样的,根据捕获组命名规则,反向引用也有两种
1- 数字反向引用:\k或\number
2- 命名反向引用:\k或’name’

反向引用通常和捕获组是一同使用的,它的作用主要是用来查找一些重复的内容或者做替换指定字符。比如要查找一串字母"aabbbbgbddesddfiid"里成对的字母。

我们捋捋思路:

  • 首先我们要有一个匹配字母的捕获组:(\w)
  • 然后(\w)\1

这样就可以了,\1代表的是1分组,这样就是一个匹配成对字母的正则式了。

如何使用正则表达式


位于 System.Text.RegularExpressions 空间下的 Regex 可以对正则表达式进行处理。

Match

这是匹配结果的对象,内含这几个常用的属性及方法

  • Value:匹配值
  • Groups:分组
  • Index:匹配值的第一个字符的索引
  • Success:是否符合正则式
  • NextMatch:下一个符合的匹配值
Regex.Matches

匹配多个符合的结果,返回一个MatchCollection数组,使用foreach并转换成Match对象进行访问.

  • IsMatch:是否符合正则式
  • Replace:替换匹配上正则式的字符串
  • Split:按匹配上的字符串进行分割
  • Match:返回第一个符合正则式的字符串
  • Matches:返回所有符合的字符串

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Cool2Feel

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值