- A+
显示不全请点击全屏阅读
常用正则表达式:http://www.cnseay.com/archives/1106
1.1 概述
.NET Framework SDK 提供了大量的正则表达式工具,使您能够高效地创建、比较和修改字符串,以及迅速地分析大量文本和数据。
正则表达式在很多语言中都会用到,其内容几乎是独立于具体语言,因此,本章与其他章节联系不是很大。但这并不意味着正则表达式的用处不大。事实上,正则表达式有着非常广泛的应用。本章主要介绍正则表达式在JavaScript中的应用。
正则表达式的英文是regular expression,意思是符合某种规则的表达式,可以将其理解为一种对文字进行模糊匹配的语言。正则表达式用一些特殊的符号(称为元字符)来代表具有某种特征(例如,某一字符必须是数字字符)的一组字符以及指定匹配的的次数,含有元字符的文本不再表示某一具体的文本内容,而是形成了一种文本模式,可以匹配符合该模式的所有文本串。
在程序语言中引入正则表达式,可以完成以下功能。
Ø 测试字符串的某个模式。例如,可以对一个输入字符串进行测试,看在该字符串是否存在一个电话号码或一个身份证号码。这称为数据有效性验证。
Ø 替换文本。可以在文档中使用一个正则表达式来标识特定文字,然后全部将其删除,或替换为其他文字。
Ø 根据模式匹配从字符串中提取一个子字符串。可以用来在文本或输入字段中查找特定文字。
1.1.1 常用正则表达式元素
字符转义
大多数重要的正则表达式语言运算符都是非转义的单个字符。转义符 【\】(单个反斜杠)通知正则表达式分析器反斜杠后面的字符不是运算符。例如,分析器将星号 【*】 视为重复限定符,而将后跟星号的反斜杠 【\*】 视为 Unicode 字符 002A。
Ø 【\a】与响铃(警报)\u0007 匹配。
Ø 【\b】匹配一个单词边界,也就是指单词和空格间的位置。例如:
er\b 可以匹配never 中的 er,但不能匹配 verb 中的 er。
其他还有很多,如:【\n】表示换行;【\r】表示回车;【\t】表示制表符等等。
限定符和限位符
表示字符或数字出现的次数以及所在的位置。
Ø 【^】表示起始位置的字符串。例如:^o表示必须以字符o开头。open正确;box错误;Open错误。
Ø 【$】表示结束位置的字符串。例如:abc$表示必须以字符串abc结束。Aabc正确;abca错误。
Ø 【*】表示重复零次或更多次。例如:a*,所有的字符串都正确,因为可以不出现a字符。
Ø 【+】表示重复一次或更多次。例如:
a+,abcad正确;bcd错误,因为字符a没有出现。
abc+,abcde正确;abdce错误,因为字符串abc没有出现。
Ø 【?】表示重复零次或一次。
Ø 【{n}】表示重复n次。例如:
o{2},food正确;box错误,因为o只出现一次;foodBox正确,匹配food中的2个o。
Ø 【{n,}】表示重复n次或更多次。
Ø 【{n,m}】表示重复n到m次。
字符类
字符类表示一组可以匹配输入字符串的字符。组合原义字符、转义符和字符类以构成正则表达式模式。
Ø 【.】表示匹配除换行符【\n】以外的任意字符。
Ø 【[char]】(正字符分组)匹配指定字符分组内的任何字符。例如:
[abc],表示小写abc中的任意一个字符。a正确;d错误。
Ø 【[^char]】(负字符分组)匹配不在指定字符分组内的任何字符。例如:
[^abc],表示不是小写abc中间的任意一个字符。d正确;a错误。
Ø 【[char-char]】(字符范围)匹配字符范围中的任何字符。例如:
[a-z],表示小写的a-z之间的任意一个字符。a正确;A错误。
Ø 【\w】表示匹配任意一个单词字符。等同于[a-zA-Z_0-9]。例如:\w,A正确;@错误。
Ø 【\W】表示不匹配任意一个单词字符。等同于[^a-zA-Z_0-9]。例如:\W,@正确;A错误。
Ø 【\d】表示一个十进制数字。等同于[0-9]。
Ø 【\D】表示一个非十进制数字。等同于[^0-9]。
Ø 【\s】表示匹配任意空白符的字符。
Ø 【\S】表示匹配任意不是空白符的字符。
分支条件
正则表达式里的分支条件指的是有几种规则,如果满足其中任意一种规则都应该当成匹配,具体方法是用【|】把不同的规则分隔开。
例如:^([a-n]|[O-Z]),表示只能以小写的a-n或者大写的O-Z开头。Book错误;book正确;open正确;Open正确。
使用分支条件时,要注意各个条件的顺序。匹配分支条件时,将会从左到右地测试每个条件,如果满足了某个分支的话,就不会去再管其它的条件了。
例如:将刚才的正则表达式中的括号去掉,^[a-n]|[O-Z],就会表示以小写的a-n开头或包含大写的O-Z。
1.1.2 Capture、Match、MatchCollection
Capture表示表示单个子表达式捕获中的结果。拥有Index、Length、Value属性。
Match类表示正则表达式匹配操作的结果。Match类无法进行实例化,需要从Regex类中产生。继承于Capture类。
MatchCollection表示通过以迭代方式将正则表达式模式应用于输入字符串所找到的成功匹配的集合。该集合为不可变(只读)的,并且没有公共构造函数。MatchCollection的实例是由Regex.Matches方法返回的。
Match类的常用方法和属性:
GroupCollection Groups属性:获取由正则表达式匹配的组的集合。
int Index属性:原始字符串中根据正则表达式发现捕获的子字符串的第一个字符的位置。例如:字符串abcd经过[bcd]匹配后,Match对象返回的Index就是1。
int Length属性:根据正则表达式捕获的子字符串的长度。例如:字符串abcd经过bc匹配后,Match对象返回的Length就是2。
Match NextMatch()方法:从上一个根据正则表达式匹配结束的位置(即在上一个匹配字符之后的字符)开始返回一个包含下一个匹配结果的新Match。例如:字符串abcd经过[ab]匹配后,返回的Match就是从b开始匹配的结果。
bool Success属性:判断正则表达式匹配是否成功。
string Value属性:获取根据正则表达式匹配捕获的子字符串。例如:字符串abcd经过[ab]匹配后,结果为a。
1.1.3 Regex类
Regex类表示不可变(只读)正则表达式类。它还包含各种静态方法,允许在不显式创建其他类的实例的情况下使用其他正则表达式类。
构造函数中需要一个正则表达式作为参数。
下面的代码示例演示如何使用正则表达式检查字符串是否是整型数字。
代码:
1. Regex regex = new Regex(@”^-?[1-9]\d*$”);
2. string[] arr = new string[] { “23”, “-43”, “-54.8”, “a1df”, “123.3” };
3. foreach (string str in arr)
4. {
5. Console.WriteLine(str + (regex.IsMatch(str) ? “是” : “不是“) +”整型“);
6. }
第1行:正则表示式为判断一个字符串是否是整数,包含0或1个【–】号,第一位数字不能是0,不包含非数字字符,以数字结尾。
第5行:利用IsMatch方法判断该字符串是否匹配正则表示式,匹配的输出“是”,否则输出“不是”。
结果
下面的代码示例演示如何使用正则表达式检查字符串并获取相应的信息。
代码:
Regex regex = new Regex(@”(\W|_)[\w]{2}”);
string content = “[email protected]”;
foreach (Match match in regex.Matches(content))
{
Console.Write(“开始下标:” + match.Index);
Console.Write(“\t值:” + match.Value);
Console.WriteLine(“\t下一个匹配:” + match.NextMatch().Value);
}
上述代码中的正则表达式声明了,匹配特殊字符或【_】,再加2个单词字符的字符串。
结果:
1.1.4 分组
我们学习了怎么重复单个字符(直接在字符后面加上限定符就行了);但如果想要重复多个字符又该怎么办?可以用小括号来指定子表达式(也叫做分组),然后就可以指定这个子表达式的重复次数了,也可以对子表达式进行其它一些操作。
例如:要求为一个软件设计生日的正则表达式,能匹配1900.01.01-2050.12.31的日期。
首先分析,整个的正则表达式应该4个年份数字+【.】+2个数字+【.】+2个数字。
然后设计年份,[12]\d{3},这个设计说明是首位是1或2,然后是3位数字,但是存在缺陷,因为可能会产生1000或2999年。因此,首先判断如果是19XX年,说明后面2个数字可以任意安排;如果是20XX年,则需要第3位只能是0-5,但是如果第3位是5的话,则第4位又只能是0。最后结果年份的正则表达式为:(19\d{2})|(20(([0-4]\d)|(50)))。
接着设计月份和日期,由于月份和日期是同步的,所以要一起设计,因为每个月的天数不一样。(这里暂时不考虑闰年平年的问题,将2月均设为28天,否则的分组量会急剧加大)。首先判断月份如果是0X,则第2位可以任意;如果是1X,则第2位只能是0-2之间。而天数则是0X、1X、20-28、30-31多种情况,因此此处判断分组较多。
如果该月是31天的则:((0[13578])|(1[01])).((0[1-9])|([12]\d)|(3[01]))。
如果该月是30天的则:((0[469])|(11)).((0[1-9])|([12]\d)|(30))。
如果该月是28天的则:02.((0[1-9])|(1\d)|(2[0-8]))。
最后生日的正则表达式为:
^((19\d{2})|(20(([0-4]\d)|(50)))).((0[13578])|(1[02])).((0[1-9])|([12]\d)|(3[01]))|((0[469])|(11)).((0[1-9])|([12]\d)|(30))|02.((0[1-9])|(1\d)|(2[0-8]))$。
由于正则表达式中并不提供关于数学的任何功能,所以只能使用冗长的分组,选择,字符类来描述。
1.1.5 Group类和GroupCollection类
Group 表示单个捕获组的结果。一个捕获组可以在单个匹配中捕获零个、一个或更多的字符串,因此 Group 提供 Capture 对象的集合。Group继承与Capture类。
表示捕获组的集合。GroupCollection 返回单个匹配中的捕获组的集合。
下列获取匹配后的分组结果。
代码:
Regex regex = new Regex(@”(\W|_)[\w]{2}”);
string content = “[email protected]”;
foreach (Match match in regex.Matches(content))
{
GroupCollection groups = match.Groups;
foreach (Group group in groups)
{
Console.Write(group.Value + “\t”);
}
Console.WriteLine();
}
结果:
Tags:
如果您喜欢我的博客,欢迎点击图片定订阅到邮箱 也可以点击链接【订阅到鲜果】
如果我的想法或工具帮助到了你,也可微信扫下方二维码打赏本人一杯咖啡