正则表达式
作用:
- 校验字符串是否满足规则
- 在一段文本中查找满足要求的内容
字符类(只匹配一个字符)
说明 | |
---|---|
[abc] | 只能是a,b或c |
[^abc] | 除了a,b,c之外的任何字符 |
[a-zA-Z] | a 到 z, A 到 Z(范围) |
[a-d[m-p]] | a 到 d, 或 m 到 p |
[a - z && [def]] | a 到 z和def的交集。为: d, e, f |
[a - z && [^bc]] | a 到 z和非bc的交际 ( 等同于[ad-z] ) |
[a-z&&[^m-p]] | a 到 z和除了m到p的交集 |
Demo:
public class RegexDemo1 {public static void main(String[] args) {System.out.println("-------------1----------------");String str1 = "a";System.out.println(str1.matches("[abc]"));//trueSystem.out.println(str1.matches("[a-c]"));//trueSystem.out.println(str1.matches("[^a-c]"));//trueSystem.out.println("ab".matches("[a-c]"));//false 原因: [a-c]只能匹配一个,有两个字符要去匹配两次System.out.println("ab".matches("[a-c][a-c]"));//trueSystem.out.println("-------------2----------------");System.out.println("n".matches("[a-d[m-p]]"));//trueSystem.out.println("nn".matches("[a-d[m-p]]"));//falseSystem.out.println("nn".matches("[a-d[m-p]][a-d[m-p]]"));//trueSystem.out.println("-------------3----------------");//如果要表示两个范围的交集, 要用 &&//如果只写一个 & ,则仅仅是表示一个字符 &System.out.println("a".matches("[a-z&&[def]]"));//falseSystem.out.println("d".matches("[a-z&&[def]]"));//trueSystem.out.println("a".matches("[a-z&[def]]"));//trueSystem.out.println("-------------4----------------");System.out.println("a".matches("[a-z&&[^def]]"));//trueSystem.out.println("d".matches("[a-z&&[^def]]"));//false}
}
预定义字符(只匹配一个字符)
表达式 | 字符 |
---|---|
. | 任何字符 |
\d | 一个数字: [0-9] |
\D | 非数字: [^0-9] |
\s | 一个空白字符: [\t\n\x0B\f\r] |
\S | 非空白字符: [^\s] |
\w | [a-zA-Z_0-9]英文、数字、下划线 |
\W | [^\w]一个非单词字符 |
Demo:
public class RegexDemo2 {public static void main(String[] args) {System.out.println("-------------1----------------");//.表示一个任意字符System.out.println("你".matches("."));//trueSystem.out.println("你n".matches("."));//falseSystem.out.println("你n".matches(".."));//trueSystem.out.println("-------------2----------------");// \d表示一个数字System.out.println("9".matches("\\d"));//trueSystem.out.println("a".matches("\\d"));//falseSystem.out.println("99".matches("\\d"));//falseSystem.out.println("99".matches("\\d\\d"));//trueSystem.out.println("-------------3----------------");// \D 表示非数字System.out.println("9".matches("\\D"));//falseSystem.out.println("a".matches("\\D"));//trueSystem.out.println("ab".matches("\\D"));//falseSystem.out.println("ab".matches("\\D\\D"));//trueSystem.out.println("-------------3----------------");// \s一个空白字符System.out.println("\t".matches("\\s"));//trueSystem.out.println("\t\t".matches("\\s"));//falseSystem.out.println(" ".matches("\\s"));//trueSystem.out.println(" ".matches("\\s"));//falseSystem.out.println("9".matches("\\s"));//falseSystem.out.println("a".matches("\\s"));//falseSystem.out.println("-------------4----------------");// \S非空白字符System.out.println("\t".matches("\\S"));//falseSystem.out.println(" ".matches("\\S"));//falseSystem.out.println("a".matches("\\S"));//trueSystem.out.println("9".matches("\\S"));//trueSystem.out.println("-------------5----------------");// \w [a-zA-Z_0-9]英文、数字、下划线System.out.println("a".matches("\\w"));//trueSystem.out.println("A".matches("\\w"));//trueSystem.out.println("0".matches("\\w"));//trueSystem.out.println("_".matches("\\w"));//trueSystem.out.println("-------------5----------------");// \W 一个非单词字符System.out.println("&".matches("\\W")); //trueSystem.out.println("a".matches("\\W")); //falseSystem.out.println("A".matches("\\W")); //falseSystem.out.println("0".matches("\\W")); //falseSystem.out.println("_".matches("\\W")); //false}
}
数量词(表中的 ‘X’ 代表任意内容)
表达式 | 说明 |
---|---|
X? | X,一次或0次 |
X* | X,零次或多次 |
X+ | X,一次或多次 |
X{n} | X,正好n次 |
X{n, } | X,至少n次 |
X{n, m} | X,至少n次但不超过m次 |
Demo:
public class RegexDemo3 {public static void main(String[] args) {System.out.println("a".matches("[abc]?"));//true 一次或0次System.out.println("".matches("[abc]?"));//trueSystem.out.println("aaa".matches("[abc]*"));//true 零次或多次System.out.println("".matches("[abc]*"));//trueSystem.out.println("".matches("[abc]+"));//false 一次或多次System.out.println("a".matches("[abc]+"));//trueSystem.out.println("aa".matches("[abc]+"));//trueSystem.out.println("aaa".matches("[abc]{3}"));//true 刚好三次System.out.println("aaaa".matches("[abc]{3}"));//falseSystem.out.println("aa".matches("[abc]{3}"));//falseSystem.out.println("aa".matches("[abc]{3,}"));//false 至少三次System.out.println("aaa".matches("[abc]{3,}"));//trueSystem.out.println("aaaa".matches("[abc]{3,}"));//trueSystem.out.println("aaa".matches("[abc]{3,4}"));//true//至少三次但不超过四次System.out.println("aaaa".matches("[abc]{3,4}"));//trueSystem.out.println("aa".matches("[abc]{3,4}"));//falseSystem.out.println("aaaaa".matches("[abc]{3,4}"));//false}
}
爬虫
正则表达式的对象:Pattern
文本匹配器对象:Matcher
Pattern常见方法:
(待完善)
Matcher常见方法:
(待完善)
方法名 | 说明 |
---|---|
find() | 拿着文本匹配器从头开始读取, 寻找是否有满足规则的字符串.如果没有,方法返回false,如果有,返回true |
m.group() | 该方法底层会根据find方法记录的索引进行字符串的截取,会把截取的小字符串进行返回 |
Demo1:
package RegexDemo;import java.util.regex.Matcher;
import java.util.regex.Pattern;public class crawler {public static void main(String[] args) {/*有如下文本,请按照要求爬取数据。Java自从95年问世以来,经历了很多版本,目前企业中用的最多的是ava8和ava11,因为这两个是长期支持版本,下一个长期支持版本是Java17,相信在未来不久Java17也会逐渐登上历史舞台要求:找出里面所有的JavaXX*/String str = "Java自从95年问世以来,经历了很多版本,目前企业中用的最多的是Java8和Java11," +"因为这两个是长期支持版本,下一个长期支持版本是Java17,相信在未来不久Java17也会逐渐登上历史舞台";// method1(str);//1.获取正则表达式的对象,也就是Pattern的对象Pattern p = Pattern.compile("Java\\d{0,2}");//2.获取文本匹配器的对象Matcher m = p.matcher(str);//3.利用循环while (m.find()){String s = m.group();System.out.println(s);}}private static void method1(String str) {//Pattern: 表示正则表达式//Matcher: 文本匹配器,作用按照正则表达式的规则去读取字符串,从头开始读取。在大串中去找符合匹配规则的子串。//1.获取正则表达式的对象,也就是Pattern的对象Pattern p = Pattern.compile("Java\\d{0,2}");//2.获取文本匹配器的对象//m: 文本匹配器的对象//str: 大的字符串//p: 规则//m要在str中找符号p规则的小的字符串Matcher m = p.matcher(str);//拿着文本匹配器从头开始读取, 寻找是否有满足规则的字符串//如果没有,方法返回false//如果有,返回true,在底层记录子串的起始索引和结束索引+1boolean b = m.find();//该方法底层会根据find方法记录的索引进行字符串的截取//会把截取的小字符串进行返回String s1 = m.group();System.out.println(s1);}
}
Demo2:
package RegexDemo;import java.util.regex.Matcher;
import java.util.regex.Pattern;public class crawlerTwo {public static void main(String[] args) {String s = "Java自从95年问世以来,经历了很多版本,目前企业中用的最多的是java8和Java11," +"因为这两个是长期支持版本,下一个长期支持版本是Java17,相信在未来不久Java17也会逐渐登上历史舞台";//定义正则表达式//? 理解为前面的数据Java//= 表示后面要跟随的数据//但是在获取的时候只获取前半部分// (?i) : 忽略大小写String regex1 = "((?i)Java)(?=8|11|17)";//下面两个效果相同//使用 " : " 时获取数据的时候获取全部String regex2 = "((?i)Java)(8|11|17)";String regex3 = "((?i)Java)(?:8|11|17)";//去掉Java后面后 8/11/17 的数据String regex4 = "((?i)Java)(?!8|11|17)";Pattern p = Pattern.compile(regex1);Matcher m = p.matcher(s);while (m.find()) {System.out.print(m.group() + " ");}System.out.println();Pattern p1 = Pattern.compile(regex2);Matcher m1 = p1.matcher(s);while (m1.find()) {System.out.print(m1.group() + " ");}System.out.println();Pattern p2 = Pattern.compile(regex3);Matcher m3 = p2.matcher(s);while (m3.find()) {System.out.print(m3.group() + " ");}System.out.println();Pattern p3 = Pattern.compile(regex4);Matcher m4 = p3.matcher(s);while (m4.find()) {System.out.print(m4.group() + " ");}}
}
Demo3:
package RegexDemo;import java.util.regex.Matcher;
import java.util.regex.Pattern;public class crawlerThree {public static void main(String[] args) {/*需求1∶按照ab+的方式爬取ab,b尽可能多获取需求2:按照ab+的方式爬取ab,b尽可能少获取*/String s ="Java自从95年问世以来,abbbbbbbbbbbbaaaaaaaaaaaaaaaaaa" +"经历了很多版本,目前企业中用的最多的是Java8和Java11,因为这两个是长期支持版本,下一个长期支持版本是Java17,相信在未来不久Java17也会逐渐登上历史舞台";//贪婪爬取 (Java默认)String regex = "ab+";Pattern p = Pattern.compile(regex);Matcher m = p.matcher(s);while (m.find()){System.out.println(m.group());}//非贪婪爬取 (在 " + " 后面加一个问号就行了)String regex1 = "ab+?";Pattern p2 = Pattern.compile(regex1);Matcher m2 = p2.matcher(s);while (m2.find()){System.out.println(m2.group());}}
}
正则表达式在字符串方法中的使用:
方法名 | 说明 |
---|---|
matches(String regex) | 判断字符串是否满足正则表达式规则 |
replaceAll(String regex, String newstr) | 按照正则表达式规则进行替换 |
split(String regex) | 按照正则表达式的规则切割字符串 |
Demo4:
package RegexDemo;public class crawlerFour {public static void main(String[] args) {/*有一段字符串:小诗诗dqwefqwfqwfwq12312小丹丹dqwefqwfqwfwq12312小惠惠要求1:把字符串中三个姓名之间的字母替换为vs要求2:把字符串中的三个姓名切割出来*/String s = "小诗诗dqwefqwfqwfwq12312小丹丹dqwefqwfqwfwq12312小惠惠";String result1 = s.replaceAll("[\\w && [^_]]+", "vs");System.out.println(result1);String[] s1 = s.split("[\\w &&[^_]]+");for (int i = 0; i < s1.length; i++) {System.out.println(s1[i]);}}
}
最后:欢迎大家关注我的公众号