http://www.icoolxue.com/album/show/237
- 普通字符:字母、汉子、数字、下划线、没有特殊意义的标点和符号
表达式中的普通字符在匹配一个字符串的时候,匹配与之相同的一个字符
- 转义字符:
第一类:\n \t \
第二类:^ $ . ( ) { } ? + * | [ ]
- 标准字符集合:
\d: 0-9任意一个数字,只匹配一个字符
\w: 任意一个字母、汉子、数字、下划线,即AZ,az,0~9,_,只匹配一个字符,不匹配其他符号,如标点符号、括号、控制字符、空白符
\s: 空格、制表符、换行符等看空白字符中的一个,只匹配一个字符
.: 可以匹配任意一个字符,除了换行符,只匹配一个字符
\D:\d的取反,即非数字,只匹配一个字符
\W: \w的取反,只匹配一个字符
\S: \s的取反,只匹配一个字符
- 自定义字符集和:
[一个或多个字符或字符集合]:能够匹配[]中的任意一个字符,只匹配一个字符
[^一个或字符或字符集合]:匹配不在[]中的任何一个字符,只匹配一个字符
[2-8]:: 匹配2-8的任意数字,只匹配一个字符
注:
正则表达式的特殊字符被包含在中括号中则失去其特殊意义,除了^-之外
标准字符集合除了小数点外,如果被包含在中括号中,则包含该标准字符集合,如:[\d.-+]将匹配 数字、小数点、-、+中的任意一个字符
- 量词:
修饰匹配次数的特殊符号:
{n}: 表达式出现n次,和将表达式手工复制n次效果相同,只修饰他前面的一个符号,不修饰多个符号的组合,若要修饰它前面的多个符号的组合需要借助括号使其形成一个表达式组
{m,n}: 意思同上,这里表示表达式最少出现m次最多出现n次
注意,此时分为贪婪模式和非贪婪模式,默认为贪婪模式
-
贪婪模式:匹配的字符越多越好,为默认模式,如:\d{3,5}匹配12345678的12435,但678匹配不了
-
非贪婪模式:匹配的字符越少越好,需要在{m,n}后加上?,即{m,n}?,如:\d{3,5}?只能匹配12345的123,
{m,}:意思同上,表达式至少出现m次,
?:表达式出现0次或一次,相当于{0,1}
+:表达式至少出现一次,相当于{1,}
*:表达式出现0次或一次,相当于{0,}
- 字符边界:零宽的
字符边界匹配的不是字符,而是位置,匹配的是符合某种条件的位置;
字符边界是零宽的,即不占用任何字符的位置,空格、制表符、换行符等看空白字符中
^: 表示匹配字符串的开头,即从字符串的开头匹配,不匹配换行符;如:表达式i匹配iiiiii中的每一个i,而表达式^i只匹配第一个i
: 表 示 匹 配 字 符 串 的 结 尾 , 即 从 字 符 串 的 结 尾 向 前 匹 配 , 不 匹 配 换 行 符 , 如 : i : 表示匹配字符串的结尾,即从字符串的结尾向前匹配,不匹配换行符,如:i :表示匹配字符串的结尾,即从字符串的结尾向前匹配,不匹配换行符,如:i只匹配最后一个i
\b: 匹配一个单词的边界,表示这样一个位置:前面的字符和后面的字符不全是\w,如:i\b匹配ai和(ai),不匹配i123,\bi匹配(iu,不匹配ai,\bi\bi不匹配(i)i
7.正则表达式的匹配模式
IGNORECASE:忽略大小写
SIGLELINE:单行模式:将整个文本看做一个字符串,使用.小数点可以匹配包含换行符\n在内的任意字符,整个文本只有一个开头和结尾
MULTILINE:多行模式:每一行作为一个字符串,每一行有开头和结尾,如果在多行模式的时候匹配整个文本的开始和结束时,使用\A和\Z
- 选择符和分组与捕获
|:分支:匹配左边或右边
():捕获组(会保存在内存中):
1.在被修饰匹配次数的时候,括号中的表达式可以作为整体被修饰
2.取匹配结果的时候括号中的表达式匹配到的内容可以被单独得到
3.每一对括号会匹配一个编号,使用()的捕获根据左括号的顺序从1开始自动编号,捕获元素编号为0的第一个捕获是由整个正则表达式模式匹配的文本
例:
([a-z]{2})\1匹配goto toto todo dodo中的toto和dodo而不匹配goto和todo,\1表示将前面匹配到的结果重复一次,而不是将前面的表达式重复一次
(?:Expression):非捕获组:即只使用(),而不保存()中的内容从而抵消()捕获组占内存的副作用
\nnn:反向引用:前面已介绍,\后面可以接一个多位数,使用()的捕获根据左括号的顺序从1开始自动编号,如(()())(())
注意:在文本编辑器替换前面捕获的匹配内容时,使用$n,n表示前面捕获的第几组,如:
原始:abc,123,cba
查找:(\w+),(\d+),(\w+)
替换:$1-$2-$3
结果:abc-123-cba
- 预搜索(零宽断言)
(?=exp):断言自身出现的位置的后面能匹配表达式exp
如:[a-z]+(?=\d\d)匹配going go22 to33中的 go22中的go和to333中的to
(?!exp):断言自身出现的位置的后面不能匹配表达式exp
如:[a-z]+(?!\d\d)匹配going go1 to22 eat333中的going go t ea, 注意匹配go1中的go而不是g;
(?<=exp):断言自身出现的位置的前面能匹配表达式exp
如:
(?<!exp):断言自身出现的位置的前面不能匹配表达式exp
如:(?<!\d\d)[a-z]+匹配going go1dd to22d eat33dd 2d中的
零宽:只进行子表达式的匹配,匹配内容不计入最终的匹配结果
占有字符:如果子表达式匹配到的是字符内容,而非位置,并被保存到最终的匹配结果中,那么就认为这个子表达式是字符占有的;
是字符占有还是零宽,是针对匹配内容是否保存到最终的匹配结果中而言;
- Java中使用正则表达式
类:Pattern:正则表达式的编译表示形式;
Pattern p=Pattern.compile(reg,int):建立正则表达式,并启用相应的模式
类:Matcher:通过解释Pattern对character sequence执行匹配操作的引擎
Matcher m=p.matcher(str):匹配字符串str
正则表达式的基本用法:
m.matches():尝试将整个字符序列与该表达式进行匹配
m.find():扫描输入的字符串,查找是否有与该模式匹配的下一个子序列
m.find()和m.group():先找到下一个子序列,然后取出与该模式匹配的子序 列的内容
正则表达式的高级用法:
m.find()和m.group():
m3.group()):返回该次匹配的所有
m3.group(0):同上
m3.group(1):返回该次匹配的第一个捕获组
m3.group(2):返回该次匹配的第二个捕获组
m3.group(i):当i值大于reg中的捕获组的总个数时,会出现数组越界异常
例:
String exp3="([a-z]+)([0-9]+)";
String str3=“a1#ab12#abc123”;
Pattern p3=Pattern.compile(exp3);
Matcher m3= p3.matcher(str3);
while(m3.find()){
System.out.println("---------------------");
System.out.println(m3.group());
System.out.println(m3.group(0));
System.out.println(m3.group(1));
System.out.println(m3.group(2));
System.out.println(m3.group(3));
}
输出:
a1
a1
a
1
java.lang.IndexOutOfBoundsException: No group 3
替换:m.replaceAll(replaceString):将正则表达式匹配的部分全部替换为replaceString,注意:不改变原来的字符串
分割:str.split(exp): 按照exp将原来的字符串进行切割,注意:切割后不包含exp中匹配的字符
例:
String[] strArray=“a1b2c3d4”.split("\d");