模式匹配-正则表达式
主要内容:匹配内容,匹配模式,实现
Java1.4起,Java核心API就引入了java.util.regex程序包,它包括两个类:Pattern和Matcher.
Pattern是对正则表达式进行编译,得到正则表达式的表现模式。
Matcher利用Pattern得到的表现模式进行模式匹配。
Pattern类的方法简述
方法 | 说明 |
static Pettern compile(String regex,int flag) | 编译模式,参数regex表示输入的正则表达式,flag表示模式类型(Pattern.CASE_INSENSITIVE 表示不区分大小写) |
Matcher matcher(CharSequence input) | 获取匹配器,input时输入的待处理的字符串 |
static boolean matches(String regex, CharSequence input) | 快速的匹配调用,直接根据输入的模式regex匹配input |
String[] split(CharSequence input,int limit) | 分隔字符串input,limit参数可以限制分隔的次数 |
Matcher类的方法简述
方法 | 说明 |
boolean find() | 查找模式匹配 |
String group() | 获得匹配 |
String group(int number) | 获得第number个的匹配 |
可在Pattern类中查看所有通配符含义
符号 | 含义 | 实例 |
? | 子模式0次或1次 |
|
* | 子模式0次或多次 |
|
+ | 子模式1次或多次 |
|
{n} | n个字符 | [abcd]{3} |
{n,} | 至少n个字符 | [abcd]{3,} |
{n,m} | n到m个字符 | [abcd]{3,5} |
. | 任何单个字符 |
|
- | 连字符 | a-z |
\s | 空白(空格符,换行符,回车符等) |
|
\S | 非空白 |
|
\d | 数字字符 |
|
\D | 非数字字符 |
|
\w | 单词字符 | |
\W | 非单词字符 |
|
\ | 转义符 | \* 匹配* |
^上尖括号符 | [^]表示非,^表示起始符 | [^abd],^[0-9]+[a-z]* |
$ | 表示结束符 | ^[0-9]\-[a-z]+$ |
[] | 字符列表中的任意一个 | [abc]匹配abc中任意一个 |
() | 子表达式 | (abc)匹配abc |
| | 或,与()进行组合 | (ab|cd|ef) |
dws
x | 字符x |
\ | 反斜线字符 |
n | 带有八进制值0的字符n(0 <= n <= 7) |
nn | 带有八进制值0的字符nn(0 <= n <= 7) |
mnn | 带有八进制值0的字符mnn(0 <= m <= 3、0 <= n <= 7) |
xhh | 带有十六进制值 0x的字符hh |
uhhhh | 带有十六进制值 0x的字符hhhh |
t | 制表符 ('u0009') |
n | 新行(换行)符 ('u000A') |
r | 回车符 ('u000D') |
f | 换页符 ('u000C') |
a | 报警 (bell) 符 ('u0007') |
e | 转义符 ('u001B') |
cx | 对应于x的控制符 |
[abc] | a、b或c(简单类) |
[^abc] | 任何字符,除了a、b或c(否定) |
[a-zA-Z] | a到z或A到Z,两头的字母包括在内(范围) |
[a-d[m-p]] | a到d或m到p:[a-dm-p](并集) |
[a-z&&[def]] | d、e或f(交集) |
[a-z&&[^bc]] | a到z,除了b和c:[ad-z](减去) |
[a-z&&[^m-p]] | a到z,而非m到p:[a-lq-z](减去) |
. | 任何字符(与行结束符可能匹配也可能不匹配) |
d | 数字:[0-9] |
D | 非数字:[^0-9] |
s | 空白字符:[ tnx0Bfr] |
S | 非空白字符:[^s] |
w | 单词字符:[a-zA-Z_0-9] |
W | 非单词字符:[^w] |
p{Lower} | 小写字母字符:[a-z] |
p{Upper} | 大写字母字符:[A-Z] |
p{ASCII} | 所有 ASCII:[x00-x7F] |
p{Alpha} | 字母字符:[p{Lower}p{Upper}] |
p{Digit} | 十进制数字:[0-9] |
p{Alnum} | 字母数字字符:[p{Alpha}p{Digit}] |
p{Punct} | 标点符号:!"#$%&'()*+,-./:;<=>?@[]^_`{|}~ |
p{Graph} | 可见字符:[p{Alnum}p{Punct}] |
p{Print} | 可打印字符:[p{Graph}x20] |
p{Blank} | 空格或制表符:[ t] |
p{Cntrl} | 控制字符:[x00-x1Fx7F] |
p{XDigit} | 十六进制数字:[0-9a-fA-F] |
p{Space} | 空白字符:[ tnx0Bfr] |
p{javaLowerCase} | 等效于 java.lang.Character.isLowerCase() |
p{javaUpperCase} | 等效于 java.lang.Character.isUpperCase() |
p{javaWhitespace} | 等效于 java.lang.Character.isWhitespace() |
p{javaMirrored} | 等效于 java.lang.Character.isMirrored() |
p{InGreek} | Greek 块(简单块)中的字符 |
p{Lu} | 大写字母(简单类别) |
p{Sc} | 货币符号 |
P{InGreek} | 所有字符,Greek 块中的除外(否定) |
[p{L}&&[^p{Lu}]] | 所有字母,大写字母除外(减去) |
^ | 行的开头 |
$ | 行的结尾 |
b | 单词边界 |
B | 非单词边界 |
A | 输入的开头 |
G | 上一个匹配的结尾 |
Z | 输入的结尾,仅用于最后的结束符(如果有的话) |
z | 输入的结尾 |
X? | X,一次或一次也没有 |
X* | X,零次或多次 |
X+ | X,一次或多次 |
X{n} | X,恰好n次 |
X{n,} | X,至少n次 |
X{n,m} | X,至少n次,但是不超过m次 |
X?? | X,一次或一次也没有 |
X*? | X,零次或多次 |
X+? | X,一次或多次 |
X{n}? | X,恰好n次 |
X{n,}? | X,至少n次 |
X{n,m}? | X,至少n次,但是不超过m次 |
X?+ | X,一次或一次也没有 |
X*+ | X,零次或多次 |
X++ | X,一次或多次 |
X{n}+ | X,恰好n次 |
X{n,}+ | X,至少n次 |
X{n,m}+ | X,至少n次,但是不超过m次 |
XY | X后跟Y |
X|Y | X或Y |
(X) | X,作为捕获组 |
n | 任何匹配的nth捕获组 |
Nothing,但是引用以下字符 | |
Q | Nothing,但是引用所有字符,直到E |
E | Nothing,但是结束从Q开始的引用 |
(?:X) | X,作为非捕获组 |
(?idmsux-idmsux) | Nothing,但是将匹配标志idmsux on - off |
(?idmsux-idmsux:X) | X,作为带有给定标志idmsux on - off |
(?=X) | X,通过零宽度的正 lookahead |
(?!X) | X,通过零宽度的负 lookahead |
(?<=X) | X,通过零宽度的正 lookbehind |
(?<!X) | X,通过零宽度的负 lookbehind |
(?>X) | X,作为独立的非捕获组 |
一、
//只判断
String[] dataArr = { "moon", "mon", "moon", "mono" };
for (String str : dataArr) {String patternStr="m(o+)n";boolean result = Pattern.matches(patternStr, str);
if (result) {System.out.println("字符串"+str+"匹配模式"+patternStr+"成功");}
else{System.out.println("字符串"+str+"匹配模式"+patternStr+"失败");}
}
//找到匹配内容
String regex ="([A-Za-z])12";
Pattern pattern = Pattern.compile(regex);
Matcher matcher = pattern.matcher("d123456");
Boolean result = matcher.find();
while(result)
{
system.out.println(matcher.group()+":"+matcher.group(1));
result = matcher.find();
}
//匹配替换Pattern p = Pattern.compile("m(o+)n",Pattern.CASE_INSENSITIVE);
// 用Pattern类的matcher()方法生成一个Matcher对象
Matcher m = p.matcher("moon mooon Mon mooooon Mooon");
StringBuffer sb = new StringBuffer();
// 使用find()方法查找第一个匹配的对象
boolean result = m.find();
// 使用循环找出模式匹配的内容替换之,再将内容加到sb里
while (result) {
m.appendReplacement(sb, "moon");result = m.find();
}
// 最后调用appendTail()方法将最后一次匹配后的剩余字符串加到sb里;
m.appendTail(sb);
System.out.println("替换后内容是" + sb.toString());
//正则表达式切割String input="职务=GM 薪水=50000 , 姓名=职业经理人 ; 性别=男 年龄=45 ";
String patternStr="(\s*,\s*)|(\s*;\s*)|(\s+)";
Pattern pattern=Pattern.compile(patternStr);
String[] dataArr=pattern.split(input);
for (String str : dataArr) {
System.out.println(str);
}//注意这里要把复杂的模式写在前面,否则简单模式会先匹配上.String input="职务=GM 薪水=50000 , 姓名=职业经理人 ; 性别=男 年龄=45 ";
String patternStr="(\s*,\s*)|(\s*;\s*)|(\s+)";
Pattern pattern=Pattern.compile(patternStr);
String[] dataArr=pattern.split(input);
for (String str : dataArr) {
System.out.println(str);
}
二、 Pattern标记
Pattern类的静态方法
static Pattern compile(String regex, int flags)
将给定的正则表达式编译到具有给定标志的模式中。
其中的flags参数就是Pattern标记,这个标记在某些时候非常重要。
Pattern.CANON_EQ
启用规范等价。
Pattern.CASE_INSENSITIVE
启用不区分大小写的匹配。
Pattern.COMMENTS
模式中允许空白和注释。
Pattern.DOTALL
启用 dotall 模式。
Pattern.LITERAL
启用模式的字面值分析。
Pattern.MULTILINE
启用多行模式。
Pattern.UNICODE_CASE
启用 Unicode 感知的大小写折叠。
Pattern.UNIX_LINES
启用 Unix 行模式。
三、 字符串的替换
String.replace(char oldChar, char newChar)
返回一个新的字符串,它是通过用 newChar 替换此字符串中出现的所有 oldChar 而生成的。
String.replace(CharSequence target, CharSequence replacement)
使用指定的字面值替换序列替换此字符串匹配字面值目标序列的每个子字符串。
String.replaceAll(String regex, String replacement)
使用给定的 replacement 字符串替换此字符串匹配给定的正则表达式的每个子字符串。
String.replaceFirst(String regex, String replacement)
使用给定的 replacement 字符串替换此字符串匹配给定的正则表达式的第一个子字符串。
StringBuffer.replace(int start, int end, String str)
使用给定 String 中的字符替换此序列的子字符串中的字符。
StringBuilder.replace(int, int, java.lang.String)
使用给定 String 中的字符替换此序列的子字符串中的字符。
Matcher.replaceAll(String replacement)
替换模式与给定替换字符串相匹配的输入序列的每个子序列。
Matcher.replaceFirst(String replacement)
替换模式与给定替换字符串匹配的输入序列的第一个子序列。
四、字符串的切分
String[] split(String regex)
根据给定的正则表达式的匹配来拆分此字符串。
String[] split(String regex, int limit)
根据匹配给定的正则表达式来拆分此字符串。
{ "moon", "mon", "moon", "mono" }
"m(o+)n"
{ "ban", "ben", "bin", "bon" ,"bun","byn","baen"}
b[aeiou]n
{ "1", "10", "101", "1010" ,"100+"}
"\d+"
String str="薪水,职位 姓名;年龄 性别";
String[] dataArr =str.split("[,\s;]");
String[] dataArr =str.split("[,\s;]");
String str="2007年12月11日";
Pattern p = Pattern.compile("[年月日]");
String[] dataArr =p.split(str);
Pattern p = Pattern.compile("[年月日]");
String[] dataArr =p.split(str);
六、注意点
1:String rex="\\[Pop3Server-15\\] \\[.*oip=(.*)\\]";
在正则表达式中[]属于特殊字符
七、正则表达式应用
1:模式匹配最大匹配原则
2:找到字符串中所有满足要求的内容
String regEx = "<a>(\\w+)</a>";
String s = "<a>123</a><a>456</a><a>789</a>";
Pattern pat = Pattern.compile(regEx);
Matcher mat = pat.matcher(s);
while(mat.find()){
System.out.println(mat.group(0));
}
<a>123</a>
<a>456</a>
<a>789</a>