该文章Github地址:https://github.com/AntonyCheng/java-notes
在此介绍一下作者开源的SpringBoot项目初始化模板(Github仓库地址:https://github.com/AntonyCheng/spring-boot-init-template & CSDN文章地址:https://blog.csdn.net/AntonyCheng/article/details/136555245),该模板集成了最常见的开发组件,同时基于修改配置文件实现组件的装载,除了这些,模板中还有非常丰富的整合示例,同时单体架构也非常适合SpringBoot框架入门,如果觉得有意义或者有帮助,欢迎Star & Issues & PR!
上一章:由浅到深认识Java语言(24):Date类
37.正则表达式
定义:
正则表达式(regular expression)描述了一种字符串匹配的模式(pattern),可以用来检查一个串是否含有某种子串、将匹配的子串替换或者从某个串中取出符合某个条件的子串等。
作用:
正则表达式能够快速匹配字符串,得到一个结果,例如手机号码格式正确与否,身份证号格式正确与否,邮箱格式正确与否等;
完事万物皆对象:
所以正则表达式也是一个对象—— Pattern;
Pattern类
正则表达式的编译表示形式。
指定为字符串的正则表达式必须首先被编译为此类的实例。然后,可将得到的模式用于创建 Matcher
对象,依照正则表达式,该对象可以与任意字符序列
匹配。执行匹配所涉及的所有状态都驻留在匹配器中,所以多个匹配器可以共享同一模式。
示例如下:
匹配十一位手机号码:
package top.sharehome.Bag;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class Demo {
public static void main(String[] args) {
Pattern p = Pattern.compile("\\d{11}");//书写规则
String desString = "17388888888";
Matcher matcher = p.matcher(desString);//返回一个匹配器
boolean matches = matcher.matches();//返回匹配结果
System.out.println(matches);
}
}
打印效果如下:
Pattern字段
字段摘要 | |
---|---|
static int | CANON_EQ 启用规范等价。 |
static int | CASE_INSENSITIVE 启用不区分大小写的匹配。 |
static int | COMMENTS 模式中允许空白和注释。 |
static int | DOTALL 启用 dotall 模式。 |
static int | LITERAL 启用模式的字面值解析。 |
static int | MULTILINE 启用多行模式。 |
static int | UNICODE_CASE 启用 Unicode 感知的大小写折叠。 |
static int | UNIX_LINES 启用 Unix 行模式。 |
Pattern方法
返回类型 | 方法解释 |
---|---|
static Pattern | compile(String regex) 将给定的正则表达式编译到模式中。 |
static Pattern | compile(String regex, int flags) 将给定的正则表达式编译到具有给定标志的模式中。 |
int | flags() 返回此模式的匹配标志。 |
Matcher | matcher(CharSequence input) 创建匹配给定输入与此模式的匹配器。 |
static boolean | matches(String regex, CharSequence input) 编译给定正则表达式并尝试将给定输入与其匹配。 |
String | pattern() 返回在其中编译过此模式的正则表达式。 |
static String | quote(String s) 返回指定 String 的字面值模式 String 。 |
String[] | split(CharSequence input) 围绕此模式的匹配拆分给定输入序列。 |
String[] | split(CharSequence input, int limit) 围绕此模式的匹配拆分给定输入序列。 |
String | toString() 返回此模式的字符串表示形式。 |
正则表达式匹配套路
套路一:
- 获得一个装着指定正则表达式的 Pattern 对象;
- 将待匹配字符串装入 pattern 对象的 matcher 方法中,获得一个匹配器;
- 执行匹配器的 matches() 方法,获得匹配结果;
示例如下:
package top.sharehome.Bag;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class Demo {
public static void main(String[] args) {
Pattern p = Pattern.compile("abc");
Matcher matcher = p.matcher("abc");
boolean matches = matcher.matches();
System.out.println(matches);
}
}
打印效果如下:
套路二:
通过 Pattern 的静态方法 matches 方法直接匹配正则表达式和目标字符串,并获得结果;
示例如下:
package top.sharehome.Bag;
import java.util.regex.Pattern;
public class Demo {
public static void main(String[] args) {
boolean matches = Pattern.matches( "abc" , "abc");
System.out.println(matches);
}
}
打印效果如下:
套路三:
通过字符串自带的 matches() 方法直接匹配正则表达式和目标字符串,并获得结果;
package top.sharehome.Bag;
import java.util.regex.Pattern;
public class Demo {
public static void main(String[] args) {
boolean matches = "abc".matches("abc");
System.out.println(matches);
}
}
打印效果如下:
正则表达式的书写
字符内容
-
"."
表示一个任意字符,如字符串长度为 n,则表达为".{n}"
;示例如下:
package top.sharehome.Bag; public class Demo { public static void main(String[] args) { boolean matches = "aaa123...".matches(".{9}"); System.out.println(matches); } }
打印效果如下:
-
"\\d"
表示一个数字字符,如字符串长度为 n ,则表达为"\\d{n}"
;"\\D"
表示一个非数字字符,如字符串长度为 n ,则表达为"\\D{n}"
;示例如下:
package top.sharehome.Bag; public class Demo { public static void main(String[] args) { boolean matches1 = "123456789".matches("\\d{9}"); boolean matches2 = "abcdefghi".matches("\\D{9}"); System.out.println(matches1); System.out.println(matches2); } }
打印效果如下:
-
"\\s"
表示一个空白字符,如字符串长度为 n ,则表达为"\\s{n}"
;"\\S"
表示一个非空白字符,如字符串长度为 n ,则表达为"\\S{n}"
;示例如下“
package top.sharehome.Bag; public class Demo { public static void main(String[] args) { boolean matches1 = " ".matches("\\s{9}"); boolean matches2 = "abcdefghi".matches("\\S{9}"); System.out.println(matches1); System.out.println(matches2); } }
打印效果如下:
-
"\\w"
表示一个单词字符,如字符串长度为 n ,则表达为"\\w{n}"
;"\\W"
表示一个非单词字符,如字符串长度为 n ,则表达为"\\W{n}"
;单词字符范围:
a~z
,A~Z
,_
,0~9
;示例如下:
package top.sharehome.Bag; public class Demo { public static void main(String[] args) { boolean matches1 = "abcdefghi".matches("\\w{9}"); boolean matches2 = "+++===---".matches("\\W{9}"); System.out.println(matches1); System.out.println(matches2); } }
打印效果如下:
-
a
(以a为例)表示字符 a 本身,abc
(以abc为例)表示字符串 abc 本身;示例如下:
package top.sharehome.Bag; public class Demo { public static void main(String[] args) { boolean matches1 = "abcdefghi".matches("abcdefghi"); boolean matches2 = "123456789".matches("123456789"); System.out.println(matches1); System.out.println(matches2); } }
打印效果如下:
字符类
"[abc]"
(以 abc 为例)表示 abc 之中的某一个;
"[^abc]"
(以 abc 为例)表示非 abc 之中的某一个;
"[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]
(减去)
示例如下:
package top.sharehome.Bag;
public class Demo {
public static void main(String[] args) {
boolean matches1 = "a".matches("[abc]");
boolean matches2 = "d".matches("[^abc]");
boolean matches3 = "y".matches("[a-zA-Z]");
boolean matches4 = "n".matches("[a-d[m-p]]");
boolean matches5 = "e".matches("[a-z&&[def]]");
boolean matches6 = "d".matches("[a-z&&[^bc]]");
boolean matches7 = "l".matches("[a-z&&[^m-p]]");
System.out.println(matches1);
System.out.println(matches2);
System.out.println(matches3);
System.out.println(matches4);
System.out.println(matches5);
System.out.println(matches6);
System.out.println(matches7);
}
}
打印效果如下:
字符数量
"内容{3}"
表示内容正好出现 3 次;
"内容{3,5}"
表示内容出现 3 到 5 次;
"内容{3,}"
表示内容至少出现 3 次;
"内容1{3}内容2{4}内容3{5}"
表示内容 1 出现 3 次且内容 2 出现 4 次且内容3 出现 5 次;
"内容?"
表示内容出现零次或一次;
"内容" 表示内容出现零次或多次;*
“内容+” 表示内容出现一次或多次;
示例如下:
package top.sharehome.Bag;
public class Demo {
public static void main(String[] args) {
boolean matches1 = "aaa".matches("a{3}");
boolean matches2 = "aaaa".matches("a{3,5}");
boolean matches3 = "aaaaaa".matches("a{3,}");
boolean matches4 = "aaabbbbccccc".matches("a{3}b{4}c{5}");
boolean matches5 = "".matches("a?");
boolean matches6 = "aaaa".matches("a*");
boolean matches7 = "a".matches("a+");
System.out.println(matches1);
System.out.println(matches2);
System.out.println(matches3);
System.out.println(matches4);
System.out.println(matches5);
System.out.println(matches6);
System.out.println(matches7);
}
}
打印效果如下:
边界匹配器
^首字符
匹配行的开头位置,所以得写在第一位;
尾字符$
匹配行的结尾位置,所以得写在最后一位;
\\b
匹配单词位置;
\\B
匹配非单词边界位置;
\\A
匹配输入的开头位置;
\\G
匹配上一个匹配的结尾位置;
\\Z
匹配输入的结尾位置,仅用于最后的结束符(如果有的话);
\\z
匹配输入的结尾位置;
示例如下:
我们来匹配 “I Love You”;
package top.sharehome.Bag;
public class Demo {
public static void main(String[] args) {
String str = "I Love You";
boolean matches = str.matches("^I\\b\\s\\b\\w{4}\\b\\s\\b\\w{2}u$");
//^I表示该行以I开头,\\b表示I右边界,\\s表示I和L之间的空格,\\b表示Love左边界,\\w{4}表示Love四个单词,\\b表示Love右边界,\\s表示空格,\\b表示You左边界,\\w{2}表示Yo两个单词,\\u$表示该行以u结尾;
System.out.println(matches);
}
}
打印效果如下:
练习
练习一:
验证输入的电话号码;
package top.sharehome.Bag;
import java.util.Scanner;
public class Demo {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String reg = "^1[3456789]\\d{9}";
System.out.println("请输入你的电话号码:");
String des = sc.next();
if(des.matches(reg)) {
System.out.println("输入成功!");
}else {
System.out.println("输入失败!");
}
sc.close();
}
}
打印效果如下:
练习二:
验证输入的电子邮箱;
邮箱由大写字母开头,后跟10位字符 (数字和字母) ,最后加上 @1900SH.com;
package top.sharehome.Bag;
import java.util.Scanner;
public class Demo {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String reg = "^[A-Z][a-zA-z0-9]{10}@1900SH.com$";
System.out.println("请输入你的电子邮箱:");
String des = sc.next();
if(des.matches(reg)) {
System.out.println("输入成功!");
}else {
System.out.println("输入失败!");
}
sc.close();
}
}
打印效果如下:
练习三:
练习使用 String 类中的 replaceAll(String regex,String replacement) 方法和 split(String regex) 方法;
package top.sharehome.Bag;
import java.util.Arrays;
public class Demo {
public static void main(String[] args) {
String str = "abcdefg123456789asdhfgjkl0987654321";
//把 str 的数字替换成 -
String replaceAll = str.replaceAll("\\d", "-");
System.out.println(replaceAll);
//把 str 按照数字进行切割成多个子字符串
String[] split = str.split("\\d");
System.out.println(Arrays.toString(split));
}
}
打印效果如下: