天天看點

正規表達式基礎文法以及如何應用。

目錄

​​一、正規表達式​​

​​1、基本介紹​​

​​2、正規表達式文法​​

​​二、正則文法​​

​​1、字元比對符、選擇比對符​​

​​2、限定符​​

​​3、定位符​​

​​4、分組​​

​​三、常用類​​

​​1、基本介紹​​

​​2、分組、捕獲、反向引用​​

​​3、String 類中使用正規表達式​​

一、正規表達式

1、基本介紹

▶ 概述
  1. 一個正規表達式,就是用某種模式去比對字元串的一個公式。很多人因為它們看上去比較古怪而且複雜是以不敢去使用,不過,經過練習後就覺得這些複雜的表達式寫起來還是相當簡單的, 而且, 一旦你弄懂它們,你就能把數小時辛苦而且易錯的文本處理工作縮短在幾分鐘(甚至幾秒鐘)内完成。
  2. 正規表達式不是隻有java才有,實際上很多程式設計語言都支援正規表達式進行字元串操作!
▶ 快速入門
​​public class RegTheory {
    public static void main(String[] args) {
        //目标:比對所有四個數字
        String content = "2002fsd ke ire i2222 ";

        //1. \\d 表示一個任意的數字
        String regStr = "(\\d\\d)(\\d\\d)";

        //2. 建立模式對象[即正規表達式對象]
        Pattern pattern = Pattern.compile(regStr);

        //3. 建立比對器
        //說明:建立比對器 matcher, 按照 正規表達式的規則 去比對 content 字元串
        Matcher matcher = pattern.matcher(content);

        //4. 開始比對
        while (matcher.find()) {
            System.out.println("找到: " + matcher.group(0));
            System.out.println("第 1 組()比對到的值=" + matcher.group(1));
            System.out.println("第 2 組()比對到的值=" + matcher.group(2));
        }
    }
}​​      

▶ 底層源碼

        matcher.find() 完成的任務 (考慮分組),{什麼是分組,比如 (\d\d)(\d\d) ,正規表達式中有() 表示分組,第 1 個()表示第 1 組,第 2 個()表示第 2 組...}

        1. 根據指定的規則

,

定位滿足規則的子字元串

(

比如

(20)(02))

        2. 找到後,将 子字元串的開始的索引記錄到

matcher

對象的屬性

int[ ] groups;

         ▷ groups[0] = 0 , 把該子字元串的結束的索引+1

的值記錄到

groups[1] = 4

         ▷ 記錄 1

()

比對到的字元串

groups[2] = 0 groups[3] = 2

         ▷ 記錄 2

()

比對到的字元串

groups[4] = 2 groups[5] = 4

         ▷ 如果有更多的分組.....

        3. 同時記錄 oldLast

的值為 子字元串的結束的 索引

+1

的值即

16,

即下次執行

find

時,就從

16 

開始比對。

▶ matcher.group(0) 分析

​​public String group(int group) {
    if (first < 0){
        throw new IllegalStateException("No match found");
    }

    if (group < 0 || group > groupCount()){
        throw new IndexOutOfBoundsException("No group " + group);
    }

    if ((groups[group*2] == -1) || (groups[group*2+1] == -1)){
        return null;
    }

    return getSubSequence(groups[group * 2], groups[group * 2 + 1]).toString();
}​​      

        根據 groups[0]=16 和

groups[1]=20 

的記錄的位置,從

content

開始截取子字元串傳回

就是

[16,20)

包含

16 

但是不包含索引為

20 

的位置  如果再次指向 find

方法

.

仍然安上面分析來執行。

▶ 小結

        1. 如果正規表達式有() 即分組

        2. 取出比對的字元串規則如下

        3. group(0) 表示比對到的子字元串

        4. group(1) 表示比對到的子字元串的第一組字串

        5. group(2) 表示比對到的子字元串的第 2 組字串

        6. ... 但是分組的數不能越界.

正規表達式基礎文法以及如何應用。

2、正規表達式文法

▶ 基本介紹

     如果要想靈活的運用正規表達式,必須了解其中各種元字元的功能,元字元從功能上大緻

分為:

     ①限定符,②選擇比對符,③分組組合和反向引用符,④特殊字元,⑤字元比對符,⑥定位符

▶ 元字元(Metacharacter)-轉義号

        符号說明: 在我們使用正規表達式去檢索某些特殊字元的時候,需要用到轉義符号。則檢索不到結果,甚至會報錯的。 案例:用$ 去比對 “abc$(" 會怎樣?

        在Java的正規表達式中,兩個\\ 代表其他語言中的一個\

        需要用到轉義符号的字元有以下 : " .  *  +  ()  $  /  \  ?  [  ]  ^  {  } "

二、正則文法

 1、字元比對符、選擇比對符

▶ 基本介紹
正規表達式基礎文法以及如何應用。
正規表達式基礎文法以及如何應用。
▶ 代碼實作
​​String content = "a11c8abc _ABCy @";

String regStr = "[a-z]"; //比對 a-z 之間任意一個字元

String regStr = "[A-Z]"; //比對 A-Z 之間任意一個字元

String regStr = "abc"; //比對 abc 字元串[預設區分大小寫]

String regStr = "(?i)abc"; //比對 abc 字元串[不區分大小寫]

String regStr = "[0-9]"; //比對 0-9 之間任意一個字元

String regStr = "[^a-z]"; //比對 不在 a-z 之間任意一個字元

String regStr = "[^0-9]"; //比對 不在 0-9 之間任意一個字元

String regStr = "[abcd]"; //比對 在 abcd 中任意一個字元

String regStr = "\\D"; //比對 不在 0-9 的任意一個字元

String regStr = "\\w"; //比對 大小寫英文字母, 數字,下劃線

String regStr = "\\W"; //比對 等價于 [^a-zA-Z0-9_]

// \\s 比對任何空白字元(空格,制表符等)
String regStr = "\\s";

// \\S 比對任何非空白字元 ,和\\s 剛好相反
String regStr = "\\S";

//. 比對出 \n 之外的所有字元,如果要比對.本身則需要使用 \\.
String regStr = ".";​​ 
  


 
 ​​//當建立 Pattern 對象時,指定 Pattern.CASE_INSENSITIVE, 表示比對是不區分字母大小寫. 
Pattern pattern = Pattern.compile(regStr, Pattern.CASE_INSENSITIVE);​​      
▶ 選擇比對符
正規表達式基礎文法以及如何應用。

​String content = "study hard"; String regStr = "t|a|r";​

2、限定符

▶ 基本介紹
正規表達式基礎文法以及如何應用。
正規表達式基礎文法以及如何應用。
▶ 代碼實作
​​String content = "a211111aaaaaahello";

String regStr = "a{3}"; // 表示比對 aaa
String regStr = "1{4}"; // 表示比對 1111
String regStr = "\\d{2}"; // 表示比對 兩位的任意數字字元

//細節:java 比對預設貪婪比對,即盡可能比對多的
String regStr = "a{3,4}"; //表示比對 aaa 或者 aaaa
String regStr = "1{4,5}"; //表示比對 1111 或者 11111
String regStr = "\\d{2,5}"; //比對 2 位數或者 3,4,5

//1+
String regStr = "1+"; //比對一個 1 或者多個 1
String regStr = "\\d+"; //比對一個數字或者多個數字

//1*
String regStr = "1*"; //比對 0 個 1 或者多個 1

//遵守貪婪比對
String regStr = "a1?"; //比對 a 或者 a1​​      

3、定位符

▶ 基本介紹
正規表達式基礎文法以及如何應用。
▶ 代碼實作
​​String content = "123-abc sldkjfs s dfsjf";

String content = "123-abc";

//以至少 1 個數字開頭,後接任意個小寫字母的字元串
String regStr = "^[0-9]+[a-z]*";

//以至少 1 個數字開頭, 必須以至少一個小寫字母結束
String regStr = "^[0-9]+\\-[a-z]+$";

//表示比對邊界的 han[這裡的邊界是指:被比對的字元串最後,也可以是空格的子字元串的後面]
String regStr = "han\\b";

//和\\b 的含義剛剛相反
String regStr = "han\\B";​​      

4、分組

▶ 基本介紹
正規表達式基礎文法以及如何應用。
正規表達式基礎文法以及如何應用。
▶ 代碼實作
​​String content = "hello world s7789 nn1189han";

//命名分組: 即可以給分組取名
String regStr = "(?<g1>\\d\\d)(?<g2>\\d\\d)";//比對 4 個數字的字元串

Pattern pattern = Pattern.compile(regStr);
Matcher matcher = pattern.matcher(content);

while (matcher.find()) {
    System.out.println("找到=" + matcher.group(0));
    System.out.println("第 1 個分組内容=" + matcher.group(1));
    System.out.println("第 1 個分組内容[通過組名]=" + matcher.group("g1"));
    System.out.println("第 2 個分組内容=" + matcher.group(2));
    System.out.println("第 2 個分組内容[通過組名]=" + matcher.group("g2"));
}​​      

三、常用類

1、基本介紹

▶ 概述

  ▷ java.util.regex 包主要包括以下三個類Pattern 類、Matcher 類和 PatternSyntaxException   ▷ Pattern 類

        pattern 對象是一個正規表達式對象。Pattern 類沒有公共構造方法。要建立一個Pattern 對象 調用其公共靜态方法,它傳回一個Pattern 對象。該方法接受一個正規表達式作為它的第一個參數,比如: Pattern r=Pattern.compile(pattern);

  ▷ Matcher類

        Matcher對象是對輸入字元串進行解釋和比對的引擎。 與Pattern 類一樣, Matcher 也沒有公共構造方法。 你需要調用 Pattern 對象的 matcher方法來獲得一個 Matcher對象

  ▷ PatternSyntaxException

        PatternSyntaxException 是一個非強制異常類, 它表示一個正規表達式模式中的文法錯誤。

▶ 代碼執行個體

​​public class PatternMethod {
    public static void main(String[] args) {
        String content = "hello abc hello, 努力學習";

        //String regStr = "hello";

        String regStr = "hello.*";

        boolean matches = Pattern.matches(regStr, content);

        System.out.println("整體比對= " + matches);
    }
}​​ 
  


 
 
▶ Matcher 常用類
 
 

​​public class MatcherMethod {
    public static void main(String[] args) {
        String content = "hello edu jack edutom hello smith hello edu edu";

        String regStr = "hello";

        Pattern pattern = Pattern.compile(regStr);

        Matcher matcher = pattern.matcher(content);

        while (matcher.find()) {
            System.out.println(matcher.start());
            System.out.println(matcher.end());
            System.out.println("找到: " + content.substring(matcher.start(), matcher.end()));
        }

        //整體比對方法,常用于,去校驗某個字元串是否滿足某個規則
        System.out.println("整體比對=" + matcher.matches());

        //完成如果 content 有 edu 替換成 努力學習
        regStr = "edu";
        pattern = Pattern.compile(regStr);
        matcher = pattern.matcher(content);

        //注意:傳回的字元串才是替換後的字元串 原來的 content 不變化
        String newContent = matcher.replaceAll("努力學習");

        System.out.println("newContent=" + newContent);
        System.out.println("content=" + content);
    }
}​​      

2、分組、捕獲、反向引用

▶ 基本介紹

1、分組

        我們可以用圓括号組成一個比較複雜的比對模式,那麼一個圓括号的部分我們可以看作是一個子表達式(一個分組)。

2、捕獲

        把正規表達式中子表達式(分組比對)的内容,儲存到記憶體中以數字編号或顯式命名的組裡, 友善後面引用, 從左向右,以分組的左括号為标志,第一個出現的分組的組号為1,第二個為2,以以此類推,組0代表的是整個正則式。

3、反向引用

        圓括号的内容被捕獲後,可以在這個括号後被使用, 進而寫出一個比較實用的比對式,這個我們稱為反向引用,這種引用既可以是在正規表達式内部,也可以是在正規表達式外部,内部反向引用\\分組号,外部反向引用$分組号。

▶ 經典案例

​​public class RegExp13 {
    public static void main(String[] args) {
        String content = "我....我要....學學學學....程式設計 java!";

        //1. 去掉所有的.
        Pattern pattern = Pattern.compile("\\.");
        Matcher matcher = pattern.matcher(content);
        content = matcher.replaceAll("");

        //2. 去掉重複的字 我我要學學學學程式設計 java!
        //(1) 使用 (.)\\1+
        //(2) 使用 反向引用$1 來替換比對到的内容
        // 注意:因為正規表達式變化,是以需要重置 matcher

        pattern = Pattern.compile("(.)\\1+");//分組的捕獲内容記錄到$1

        matcher = pattern.matcher(content);

        //使用 反向引用$1 來替換比對到的内容
        content = matcher.replaceAll("$1");

        System.out.println("content=" + content);
    }
}​​      

3、String 類中使用正規表達式

▶ 替換功能

        String 類: 

public String replaceAll(String regex,String replacement)

▶ 判斷功能

        String 類: 

public boolean matches(String regex){}

//

使用

Pattern

Matcher

▶ 分割功能

        String 類: 

public String[] split(String regex)

​​String content = "2000 年 5 月,JDK1.3、JDK1.4 和 J2SE1.3 相繼釋出。";

//使用正規表達式方式,将 JDK1.3 和 JDK1.4 替換成 JDK
content = content.replaceAll("JDK1\\.3|JDK1\\.4", "JDK");

System.out.println(content);​​ 
  

​​//要求 驗證一個 手機号, 要求必須是以 138 139 開頭的
content = "13888889999";

if (content.matches("1(38|39)\\d{8}")) {
    System.out.println("驗證成功");
} else {
    System.out.println("驗證失敗");
}​​ 
   

​​//要求按照 # 或者 - 或者 ~ 或者 數字 來分割
content = "hello#abc-jack12smith~北京";

String[] split = content.split("#|-|~|\\d+");

for (String s : split) {
    System.out.println(s);
}​​