@azmddy
2018-07-23T10:05:43.000000Z
字数 3558
阅读 431
C++
正则表达式 Regex(Regular Expression)是描述或匹配某个句法规则的字符串,用于检索、替换那些匹配某个模式的文本。
一个正则表达式通常被称为一个模式。由表达式、量词、断言组成。
表达式可以是以下项之一:
一般的字符,可匹配目标序列中相同的字符。
例如:a 只能匹配 a; abc只能匹配abc。
通配符 .,可匹配目标序列中除了换行符外的任何字符。
例如:a.c 可以匹配abc、a c、a.c、a1c等等。
[expr] 形式的括号表达式,可以匹配目标序列中包含在表达式expr定义集内的字符或者排序规则表达式;采用[^expr],可匹配目标序列中未包含在表达式expr定义集内的字符或排序规则表达式。
表达式expr可以包含下列的任意组合:
[A] 匹配 Ach1-ch2形式的字符域。例如 [A-F] 匹配大写字母A到F中的任何一个字母,比如:匹配 A.[:name:]形式的字符类。例如:[[:alpha:]] 匹配一个字母(不区分大小写)。| 字符类名 | 说明 |
|---|---|
| alnum | 字母(不区分大小写)和数字 |
| alpha | 字母(不区分大小写) |
| blank | 空格或制表符 |
| cntrl | 文件格式转义字符 |
| digit | 数字 |
| graph | 字母(不区分大小写)、数字和英文标点 |
| lower | 小写字母 |
| upper | 大写字母 |
| 字母(不区分大小写)、数字、英文标点和空格 | |
| punct | 英文标点 |
| sapce | 空格 |
| xdigit | 表示十六进制的字符(数字,a,b,c,d,e,f,A,B,C,D,E,F) |
| d | 与digit相同 |
| s | 与space相同 |
| w | 与alnum相同 |
定位点。定位点^匹配目标序列的开头,$可匹配目标序列的末尾。
定位点可匹配目标字符串中的位置,而不匹配字符。
转义序列
文件格式转义。
\\、\f、\n、\r、\t和\v,他们分别匹配目标序列中的反斜杠、换页符、回车符、水平制表符合垂直制表符。
DSW字符转义
| 转义序列 | 等效命名类 | 默认命名类 |
|---|---|---|
\d |
[[:d:]] |
[[:digit:]] |
\D |
[^[:D:]] |
[^[:digit:]] |
\s |
[[:s:]] |
[[:space:]] |
\S |
[^[:S:]] |
[^[:space:]] |
\w |
[[:w:]] |
[a-zA-Z0-9] |
\W |
[^[:W:]] |
[^a-zA-Z0-9] |
\ooo,"ooo"表示三位的八进制数,例如:\101 匹配字符 A。\xhh,"hh"表示两位的十六进制数,例如:\x41 匹配字符 A。\uhhhh,"hhhh"表示四位的十六进制数,例如:\u0041 匹配字符A。一个量词指定了要匹配的表达式出现的次数。例如,x{1,1} 表示必须且只能匹配一个字符x,而x{1,3}表示至少匹配一个x,最多匹配三个x。
| 量词 | 含义 |
|---|---|
| E? | 匹配0次或者1次 E(表达式),等价于 E{0,1} |
| E+ | 至少匹配一次 E,等价于 E{1,} |
| E* | 匹配0次或者多次 E,等价于 E{0,} |
| E{n} | 匹配n次E,等价于E{n,n} |
| E{n,} | 至少匹配n次E |
| E{,m} | 至多匹配m次E |
| E{n,m} | 至少匹配n次,至多匹配m次E |
例如:[A-C]+, 可匹配 AAA 、B
| 断言 | 含义 |
|---|---|
| \b | 一个单词的边界 |
| \B | 一个非单词的边界 |
| (?=E) | 表达式后面紧跟着E才匹配成功,但不会改名目标序列中匹配的位置 |
| (?!E) | 表达式后没有紧跟着E才匹配成功,但不会改名目标序列中匹配的位置 |
| (?:E) | 表达式后面紧跟着E才匹配成功 |
例如:
\\bmail\\b 匹配的就是一个单词mail。
This is a T(?!est)表示如果T后面没有est就匹配,这主要用于替换,后面会有实例。
This is a T(?=est)表示如果T后面有est就匹配,这主要用于替换,后面会有实例。
在C++中使用正则表达式需要用到regex库。
默认情况下,正则表达式遵循ECMAScript语法。
常用函数:
| 函数名称 | 解释 |
|---|---|
| regex_match | 将一个字符序列与正则表达式进行匹配。 |
| regex_search | 查找字符序列中与正则表达式匹配的结果,找到第一个之后就会返回结果并停止查找。 |
| regex_replace | 替换字符到正交表达式匹配到字符序列的位置。 |
邮箱的一般格式:xxx@xxx.com
验证 xxx@163.com 格式的邮箱。
正则表达式:[[:graph:]]+@163[.]com,这里将.用方括号括起来是因为.在正在表达式中是一个通配符。
#include <regex>#include <iostream>using namespace std;int main(){string re = "[[:graph:]]+@163[.]com";regex rule(re);string str = "acvds.cpp@163.com";cout << regex_match(str, rule) << endl; //truesystem("pause");return 0;}
原理:
IP地址是有四个用小数点隔开的十进制整数(0~255)组成的,每个整数的位数不确定,以及整数是不同位数的时候,每个位上数字的取值范围也会存在差异,所以需要一一匹配。
当整数是一位的时候,取值是0~9,正则表达式\\d(反斜杠需要转义);
当整数是两位的时候,取值是0~9,正则表达式\\d{1,2};
当整数是三位的时候,当最高位是1的时候,其它两位的取值是0~9,正则表达式1\\d{1,2};当最高位是2的时候,其它两位的取值是0~5,正则表达式2[0-5]{1,2};
然后用|(或)连接。
#include <regex>#include <iostream>using namespace std;int main(){string re = "(\\d|\\d{1,2}|(1\\d{1,2})|2[0-5]{1,2})[.](\\d|\\d{1,2}|(1\\d{1,2})|2[0-5]{1,2})[.](\\d|\\d{1,2}|(1\\d{1,2})|2[0-5]{1,2})[.](\\d|\\d{1,2}|(1\\d{1,2})|2[0-5]{1,2})";regex rule(re);string str = "100.100.100.0";cout << regex_match(str, rule) << endl; //truesystem("pause");return 0;}
这里主要涉及到regex_replace函数的使用。
函数原型:
basic_string<_Elem, _Traits1, _Alloc1> regex_replace(const basic_string<_Elem, _Traits1, _Alloc1>& _Str,const basic_regex<_Elem, _RxTraits>& _Re,const _Elem *_Ptr,regex_constants::match_flag_type _Flgs =regex_constants::match_default);
一共四个参数,第一个参数是目标字符串,第二个参数是正则表达式规则,第三个是用于替换的字符串, 第四个是设置正则表达式如何匹配以及格式化用于替换的字符串。
#include <regex>#include <iostream>using namespace std;int main(){string re1 = "i";string re2 = "love";string re3 = "you";regex rule1(re1);regex rule2(re2);regex rule3(re3);string str = " i love you.";str = regex_replace(str, rule1, "我");str = regex_replace(str, rule2, "喜欢");str = regex_replace(str, rule3, "你");cout << str << endl;//我喜欢你system("pause");return 0;}
#include <regex>#include <iostream>using namespace std;int main(){string re = "E(?!xpression)";regex rule(re);string str = "Regular E";cout << regex_replace(str,rule,"Expression") << endl; //Regular Expressionsystem("pause");return 0;}
正则表达式一个非常有用的利器,掌握它需要多加练习,实践出真知!
如果想了解更多关于正则表达的内容,清点击以下链接:
链接1
链接2