java 正则表达式用法
最近学习编译原理,要用到正则表达式。本次要学习如何用java正则表达式。
正则表达式:可以用来搜索、编辑、处理文本。
参考链接:https://my.oschina.net/CasparLi/blog/361859
类库
import java.util.regex.*
介绍
java.util.regex
是一个用正则表达式所订制的模式来对字符串进行匹配工作的类库包。
其主要包含三个类:
- Pattern类(编译)
- Matcher类(解释与匹配)
- PatternSyntaxException类(异常)
总的流程应该是这样:首先Pattern实例定制了一个正则表达式经编译后的模式,然后一个Matcher实例在这个Pattern实例的模式下进行字符串的匹配工作。
下面将逐一击破!
根据实际的例子来分析吧!
假设现在我有这串文字:
"我的QQ是:123456我的电话是:10010我的学号是:2016210000"
现在我想让电脑给我提取以上的所有数字,那可怎么办?
如果没学过正则表达式,提取是比较复杂的!
结尾告诉你怎么做!
先来学学java的正则表达式的相关函数。
1. Pattern.split(CharSequence input)
用于字符串分割
我想电脑自动帮我通过数字分割各部分
这里需要使用到正则表达式\\d+
代表的意思是:匹配字符串的每个地方的所有数字
首先,可以通过Pattern.compile
方法创建一个正则表达式对象,然后通过Pattern.split
分割。
String reg = "\\d+";
String text = "我的QQ是:123456我的电话是:10010我的邮箱是:[email protected]";
Pattern p = Pattern.compile(reg);
String[] str=p.split(text);
for(int i=0;i
可以看出通过数字分割出三个部分(不管你是什么数字)
2. Pattern.matches(String regex,CharSequence input)
用于匹配到一次即停止,如果匹配了全部字符串返回true,否则返回false
System.out.println(Pattern.matches("\\d+","1234"));
System.out.println(Pattern.matches("\\d+","1234aa"));
System.out.println(Pattern.matches("\\d+","22bb23"));
可以看出匹配完返回true,没匹配完返回false。
3. Pattern.matcher(CharSequence input)
Pattern只能做简单的匹配操作,要想得到更强的匹配操作,得结合matcher类
Pattern p=Pattern.compile(reg);
Matcher m=p.matcher(text);
通过以上方式可以构建出matcher类
4. matcher下的方法
- matches()对整个字符进行匹配,只有整个匹配才返回true
Pattern p=Pattern.compile("\\d+");
Matcher m=p.matcher("22bb23");
System.out.println(m.matches());
//false
Matcher m2=p.matcher("2223");
System.out.println(m2.matches());
//true
- lookingAt() 对前面的字符进行匹配,只有匹配到的字符串在前面才返回true
Pattern p=Pattern.compile("\\d+");
Matcher m=p.matcher("22bb23");
System.out.println(m.lookingAt());
//true
Matcher m2=p.matcher("aa2223");
System.out.println(m2.lookingAt());
//false
- find() 对字符串匹配,找到就返回true,找不到就返回false(只遍历到第一个)
Pattern p=Pattern.compile("\\d+");
Matcher m=p.matcher("22bb23");
System.out.println(m.find());
//true
Matcher m2=p.matcher("aa2223");
System.out.println(m2.find());
//true
Matcher m3=p.matcher("aa2223bb");
System.out.println(m3.find());
//true
Matcher m4=p.matcher("aabb");
System.out.println(m4.find());
//false
当matches、lookingAt、find执行匹配后,就可以利用以下三种得到更详细的信息。
- start()返回匹配到子字符串中的初始位置
Pattern p=Pattern.compile("\\d+");
Matcher m=p.matcher("aa22bb23");
System.out.println(m.find());
//返回true
System.out.println("position:"+m.start());
//索引到的初始位置为2
- end()返回匹配到子字符串的最后一个位置
Pattern p=Pattern.compile("\\d+");
Matcher m=p.matcher("aa22bb23");
System.out.println(m.find());
//返回true
System.out.println("position:"+m.end());
//索引到的结束位置为4
- group()返回匹配到的子字符串
Pattern p=Pattern.compile("\\d+");
Matcher m=p.matcher("aa22bb23");
System.out.println(m.find());
//返回true
System.out.println("text:"+m.group());
//子字符串为22
注意:这些方法的调用是有先后顺序!
这里再介绍一个 groupCount()方法,返回表达式有多少组。
不是匹配到的组,是表达式匹配的组,有多少括号就有多少组。
Pattern p=Pattern.compile("([a-z]+)(\\d+)");
Matcher m=p.matcher("a2223a");
System.out.println("groupCount1:"+m.groupCount());
//返回2
Pattern p2=Pattern.compile("(\\d+)");
Matcher m2=p2.matcher("a2223a");
System.out.println("groupCount2:"+m2.groupCount());
//返回1
Pattern p3=Pattern.compile("(([a-z]+)(\\d+))");
Matcher m3=p3.matcher("a2223a");
System.out.println("groupCount3:"+m3.groupCount());
//返回3
其实start()、end()、group()均有重构方法
start(int i),end(int i),group(int i) 专用于分组操作
start(int i)
Pattern p=Pattern.compile("([a-z]+)(\\d+)");
Matcher m=p.matcher("123aa2223ccc123dd");
int count=0;
while(m.find()) {
count++;
System.out.println("第"+count+"次的start:"+m.start());
//匹配到的文本的索引
System.out.println("第"+count+"次的start(0):"+m.start(0));
//默认为匹配到整个文本的索引
System.out.println("第"+count+"次的start(1):"+m.start(1));
//默认为匹配到的文本的第一组的索引
System.out.println("第"+count+"次的start(2):"+m.start(2));
//默认为匹配到的文本的第二组的索引
}
end(int i)
与start一样就不写了
group(int i)
Pattern p=Pattern.compile("([a-z]+)(\\d+)");
Matcher m=p.matcher("a2223ccc123");
int count=0;
while(m.find()) {
count++;
System.out.println("第"+count+"次的group:"+m.group());
//默认为匹配到的文本
System.out.println("第"+count+"次的group(0):"+m.group(0));
//默认为匹配到的整个文本
System.out.println("第"+count+"次的group(1):"+m.group(1));
//默认为匹配到的文本的第一组
System.out.println("第"+count+"次的group(2):"+m.group(2));
//默认为匹配到的文本的第二组
}
由以上的结果可以看出重构函数的i指的是表达式的组号,i为0默认为全局,i为1为第一个,后面同理。
使用
了解完以上的函数,回到上面,要实现提取一串文字的所有数字可以怎么用呢?
String reg ="\\d+";
String text="我的QQ是:123456我的电话是:10010我的学号是:2016210000";
Pattern p=Pattern.compile(reg);
String[] str=p.split(text);
Matcher m=p.matcher(text);
int index=0;//标记
while(m.find()) {
System.out.print(str[index]);
System.out.println(m.group());
index++;
}
让我们来看看结果!
结合以上的分割函数,通过数字分割,得到文字,然后再通过匹配函数,找到字符串里的所有数字,依次输出。
我也可以直接获取数字放进一个数组,这样我就存储起来了。
当然这是最基础的,我可以添加多几个正则表达式,可以匹配标准准确的邮箱,手机号,QQ号等。