简单方便的正则表达式—秒懂
正则表达式概述
是指一个用来描述或者匹配一系列符合某个语法规则的字符串的单个字符串。其实就是一种规则。有自己特殊的应用。
作用:专门用于操作字符串
特点:用一些特定的符号来表示一些代码的操作.这样就简化书写.
所以学正则表达式,就是学习一些特殊符号的使用.
好处:可以简化对字符串的操作
弊端:符号定义越多,正则越长,阅读性越差
字符类
java.util.regex包中的Pattern类中
[abc] a、b 或 c(简单类)
[^abc] 任何字符,除了 a、b 或 c(否定)
[a-zA-Z] a到 z 或 A到 Z,两头的字母包括在内(范围)
[0-9] 0到9的字符都包括
-
[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](减去)
-
-
System.out.println("10".matches(regex)); //10代表1字符和0字符,不是单个字符//false
-
String regex = "[abc]"; //[]代表单个字符
预定义字符类
. 任何字符(一个,两个点代表任意两个字符)。
\d 数字:[0-9]
\w 单词字符:[a-zA-Z_0-9]
案例:
-
\D 非数字: [^0-9]
-
\s 空白字符:[ \t\n\x0B\f\r] //空格,\t:制表符,\n:换行,\x0B:垂直制表符,\f:翻页,\r:回车
-
\S 非空白字符:[^\s]
-
\w 单词字符:[a-zA-Z_0-9]
-
\W 非单词字符:[^\w]
-
System.out.println("\\");//要打印出\,并需再加一个\进行转义
-
String regex = "\\d"; //\代表转义字符,如果想表示\d的话,需要\\d
-
String regex = "..";(一个点一个字符,两个点两个字符)
数量词
* A:Greedy 数量词
* X? X(任意字符),一次或一次也没有
* X* X,零次或多次
* X+ X,一次或多次
* X{n} X,恰好 n 次
* X{n,} X,至少 n 次
* X{n,m} X,至少 n 次,但是不超过 m 次
案例:
-
String regex = "[abc]{5,15}";
-
String regex = "[abc]{5,}";//>=5次
-
String regex = "[abc]{5}";//恰好n次
-
String regex = "[abc]+";(一次或多次)
-
String regex = "[abc]*";(0次到多次)
-
String regex = "[abc]?";(abc出现一次或一次也没有)
把给定字符串中的数字排序
需求:我有如下一个字符串:"91 27 46 38 50",请写代码实现最终输出结果是:"27 38 46 50 91"
案例:
-
import java.util.Arrays;
-
public class Test1 {
-
/**
-
* 分析:
-
* 1,将字符串切割成字符串数组(字符串排序,比较第一个不相同的字符)
-
* 2,将字符串转换成数字并将其存储在一个等长度的int数组中
-
* 3,排序
-
* 4,将排序后的结果遍历并拼接成一个字符串
-
*/
-
public static void main(String[] args) {
-
String s = "91 27 46 38 50";
-
//1,将字符串切割成字符串数组
-
String[] sArr = s.split(" ");
-
//2,将字符串转换成数字并将其存储在一个等长度的int数组中
-
int[] arr = new int[sArr.length];
-
for (int i = 0; i < arr.length; i++) {
-
arr[i] = Integer.parseInt(sArr[i]); //将数字字符串转换成数字
-
}
-
-
//3,排序
-
Arrays.sort(arr);
-
-
//4,将排序后的结果遍历并拼接成一个字符串27 38 46 50 91
-
/*String str = "";//会产生很多垃圾,不断的+,原来的就变成了垃圾
-
for (int i = 0; i < arr.length; i++) {
-
if(i == arr.length - 1) {
-
str = str + arr[i]; //27 38 46 50 91
-
}else {
-
str = str + arr[i] + " "; //27 38 46 50
-
}
-
}
-
-
System.out.println(str);*/
-
-
StringBuilder sb = new StringBuilder();
-
for (int i = 0; i < arr.length; i++) {
-
if(i == arr.length - 1) {
-
sb.append(arr[i]);
-
}else {
-
sb.append(arr[i] + " ");
-
}
-
}
-
-
System.out.println(sb);
-
}
-
-
}
正则表达式的替换功能
String类的功能:public String replaceAll(String regex,String replacement)
案例:
-
public class Demo6_ReplaceAll {
-
public static void main(String[] args) {
-
String s = "wo111ai222kailing";
-
String regex = "\\d"; //\\d代表的是任意数字
-
String s2 = s.replaceAll(regex, "");//把任意数字替换成空串
-
}
-
}
正则表达式的分组功能
正则表达式的分组功能
捕获组可以通过从左到右计算其开括号来编号。例如,在表达式 ((A)(B(C))) 中,存在四个这样的组:
1 ((A)(B(C)))
2 (A
3 (B(C))
4 (C)
案例演示
a:切割
需求:请按照叠词切割: "sdqqfgkkkhjppppkl";
b:替换
需求:我我....我...我.爱...爱爱...爱.编..编编.编.程.程.程..程
将字符串还原成:"我爱编程"。
说明
(.)\\1+的含义: (.)把任意字符存在组里,第一个位置为任意字符,第二个位置和(.)一样,但是第二个位置出现了1次或多次
(.)通过"\"形式反向引用前面的组,\\1表示第一组的内容在\\1重新出现,可以1次或多次
替换:
-
private static void demo3() {
-
String s = "我我....我...我.爱...爱爱...爱.编..编编.编.程.程.程..程";
-
String s2 = s.replaceAll("\\.+", "");
-
String s3 = s2.replaceAll("(.)\\1+", "$1");
-
说明:
-
1第三行作用为把字符串中所有点".",替换为空字符串""
-
点(.)在正则表达式中代表任意字符,它具有特殊的含义, 所以需要将点进行转义前面加\,但是要想表示出一个\,需要在前面再加一个\,这样就成了\\.
-
2第四行: 将连续重复的字符用自己本生替代
-
$1代表第一组中的内容,(.)把任意字符存在组里,
-
3第一个括号是第一组, 第二个括号,第二组,用$2
-
}
按照叠词切割字符串
-
public static void demo2() {
-
//需求:请按照叠词切割: "sdqqfgkkkhjppppkl";
-
String s = "sdqqfgkkkhjppppkl";
-
//String regex = "(.)\\1";
-
String regex = "(.)\\1+"; //+代表第一组出现一次到多次
-
String[] arr = s.split(regex);
-
-
for (int i = 0; i < arr.length; i++) {
-
System.out.println(arr[i]);
-
}
-
}
-
-
public static void demo1() {
-
//叠词 快快乐乐,高高兴兴
-
/*String regex = "(.)\\1(.)\\2"; //\\1代表第一组又出现一次 \\2代表第二组又出现一次
-
System.out.println("快快乐乐".matches(regex));
-
System.out.println("快乐乐乐".matches(regex));
-
System.out.println("高高兴兴".matches(regex));
-
System.out.println("死啦死啦".matches(regex));*/
-
-
//叠词 死啦死啦,高兴高兴
-
String regex2 = "(..)\\1";//第一组有两个字符,然后让第一组再出现一次
-
System.out.println("死啦死啦".matches(regex2));
-
System.out.println("高兴高兴".matches(regex2));
-
System.out.println("快快乐乐".matches(regex2));
-
}
-
-
}
Pattern和Matcher的概述
Pattern是regax包下的一个类,被final修饰
模式和匹配器的典型调用顺序
通过JDK提供的API,查看Pattern类的说明
典型的调用顺序是 (详看下面案例)
Pattern p = Pattern.compile("a*b");
Matcher m = p.matcher("aaaaab");
boolean b = m.matches();
案例:
-
public static void demo1() {
-
//"a*b":表示a出现的是0次或多次,后面跟一个b
-
Pattern p = Pattern.compile("a*b"); //获取到正则表达式
-
(a*b代表a出现0次或多次,后面跟b)
-
Matcher m = p.matcher("aaaaab"); //获取匹配器(里面传一个要被匹配的字符串)
-
boolean b = m.matches(); //看是否能匹配,匹配就返回true,(matches匹配器matcher里的方法)
-
}
取出字符串中的手机号
Pattern和Matcher的结合使用
需求:把一个字符串中的手机号码获取出来
步骤分4步(具体看案例):
- 拿到正则表达式Pattern.compile(regex)
- 拿到匹配器p.matcher(s)
- 拿出符合规定的字符串m.find()—一般通过while来
- 返回匹配到的子序列m.group()
案例:
-
//匹配查找手机号
-
private static void demo2() {
-
String s = "我的手机是18511866260,我曾用过18987654321,还用过18812345678";
-
String regex = "1[3578]\\d{9}"; 正则表达式
-
//第一位是1,第二位是[3578]中的任意一个,后面的是任意数字\\d,并出现9次{9} 手机号码正则表达式
-
Pattern p = Pattern.compile(regex); //拿到正则表达式
-
Matcher m = p.matcher(s); //拿到匹配器
-
while(m.find());//拿正则到字符串中找符合规定的字符串,找到返回true,找不到但会false
-
System.out.println(m.group());//返回由以前匹配操作所匹配的输入子序列
-
}