正則表達式(Regular Expression)是一種文本模式,包括普通字符(例如,a 到 z 之間的字母)和特殊字符(稱為"元字符"),可以用來檢查一個串是否含有某種子串、將匹配的子串替換或者從某個串中取出符合某個條件的子串等。
一、正則表達式語法
正則表達式包括普通字符(例如字符 a 到 z)、非打印字符(例如\n)、特殊字符(稱為"元字符")、限定符(例如{n,m})和定位符(例如^)。
1.1 普通字符
普通字符包括所有大寫和小寫字母、所有數字、所有標點符號和一些其他符號。
1.2 非打印字符
非打印字符也可以是正則表達式的組成部分。下表列出了表示非打印字符的轉義序列:
字符 | 描述 |
---|---|
\n | 匹配一個換行符。等價於 \x0a 和 \cJ。 |
\r | 匹配一個回車符。等價於 \x0d 和 \cM。 |
\s | 匹配任何空白字符,包括空格、制表符、換頁符等等。等價於 [ \f\n\r\t\v]。 |
\S | 匹配任何非空白字符。等價於 [^ \f\n\r\t\v]。 |
\t | 匹配一個制表符。等價於 \x09 和 \cI。 |
\v | 匹配一個垂直制表符。等價於 \x0b 和 \cK。 |
1.3 特殊字符
所謂特殊字符,就是一些有特殊含義的字符,在試圖匹配它們時要特別對待。若要匹配這些特殊字符,必須首先使字符"轉義",即,將反斜杠字符\ 放在它們前面。下表列出了正則表達式中的特殊字符:
特別字符 | 描述 |
---|---|
$ | 匹配輸入字符串的結尾位置。如果設置了 RegExp 對象的 Multiline 屬性,則 $ 也匹配 '\n' 或 '\r'。要匹配 $ 字符本身,請使用 \$。 |
( ) | 標記一個子表達式的開始和結束位置。子表達式可以獲取供以后使用。要匹配這些字符,請使用 ( 和 )。 |
* | 匹配前面的子表達式零次或多次。要匹配 * 字符,請使用 \*。 |
+ | 匹配前面的子表達式一次或多次。要匹配 + 字符,請使用 \+。 |
. | 匹配除換行符 \n 之外的任何單字符。要匹配 . ,請使用 \. 。 |
[ | 標記一個中括號表達式的開始。要匹配 [,請使用 \[。 |
? | 匹配前面的子表達式零次或一次,或指明一個非貪婪限定符。要匹配 ? 字符,請使用 \?。 |
\ | 將下一個字符標記為或特殊字符、或原義字符、或向后引用、或八進制轉義符。例如, 'n' 匹配字符 'n'。'\n' 匹配換行符。序列 '\' 匹配 "",而 '(' 則匹配 "("。 |
^ | 匹配輸入字符串的開始位置,除非在方括號表達式中使用,此時它表示不接受該字符集合。要匹配 ^ 字符本身,請使用 \^。 |
{ | 標記限定符表達式的開始。要匹配 {,請使用 \{。 |
| | 指明兩項之間的一個選擇。要匹配 |,請使用 \ |
(?:pattern) | 匹配 pattern 但不獲取匹配結果,也就是說這是一個非獲取匹配,不進行存儲供以后使用。這在使用 "或" 字符 (|) 來組合一個模式的各個部分是很有用。例如, 'industr(?:y|ies) 就是一個比 'industry|industries' 更簡略的表達式。 |
(?=pattern) | 正向肯定預查,在任何匹配pattern的字符串開始處匹配查找字符串。這是一個非獲取匹配,也就是說,該匹配不需要獲取供以后使用。例如,"Windows(?=2000)"能匹配"Windows2000"中的"Windows",但不能匹配"Windows3.1"中的"Windows"。 |
(?!pattern) | 正向否定預查,在任何不匹配pattern的字符串開始處匹配查找字符串。這是一個非獲取匹配,也就是說,該匹配不需要獲取供以后使用。例如"Windows(?2000)"能匹配"Windows3.1"中的"Windows",但不能匹配"Windows2000"中的"Windows"。 |
(?<=pattern) | 反向肯定預查,與正向肯定預查類似,只是方向相反。例如,"(?<=2000)Windows "能匹配"2000Windows "中的"Windows ",但不能匹配"3.1Windows "中的"Windows "。 |
(?<!pattern) | 反向否定預查,與正向否定預查類似,只是方向相反。例如"(?<!2000)Windows "能匹配"3.1Windows "中的"Windows ",但不能匹配"2000Windows "中的"Windows "。 |
1.4 限定符
限定符用來指定正則表達式的一個給定組件必須要出現多少次才能滿足匹配。有 ***** 或 + 或 ? 或 {n} 或 {n,} 或 {n,m} 共6種。正則表達式的限定符有:
字符 | 描述 |
---|---|
* | 匹配前面的子表達式零次或多次。例如,zo* 能匹配 "z" 以及 "zoo"。* 等價於{0,}。 |
+ | 匹配前面的子表達式一次或多次。例如,'zo+' 能匹配 "zo" 以及 "zoo",但不能匹配 "z"。+ 等價於 {1,}。 |
? | 匹配前面的子表達式零次或一次。例如,"do(es)?" 可以匹配 "do" 、 "does" 中的 "does" 、 "doxy" 中的 "do" 。? 等價於 {0,1}。 |
{n} | n 是一個非負整數。匹配確定的 n 次。例如,'o{2}' 不能匹配 "Bob" 中的 'o',但是能匹配 "food" 中的兩個 o。 |
{n,} | n 是一個非負整數。至少匹配n 次。例如,'o{2,}' 不能匹配 "Bob" 中的 'o',但能匹配 "foooood" 中的所有 o。'o{1,}' 等價於 'o+'。'o{0,}' 則等價於 'o*'。 |
{n,m} | m 和 n 均為非負整數,其中n <= m。最少匹配 n 次且最多匹配 m 次。例如,"o{1,3}" 將匹配 "fooooood" 中的前三個 o。'o{0,1}' 等價於 'o?'。請注意在逗號和兩個數之間不能有空格。 |
1.5 定位符
定位符用來描述字符串或單詞的邊界,^ 和 $ 分別指字符串的開始與結束,\b 描述單詞的前或后邊界,\B 表示非單詞邊界。正則表達式的定位符有:
字符 | 描述 |
---|---|
^ | 匹配輸入字符串開始的位置。如果設置了 RegExp 對象的 Multiline 屬性,^ 還會與 \n 或 \r 之后的位置匹配。 |
$ | 匹配輸入字符串結尾的位置。如果設置了 RegExp 對象的 Multiline 屬性,$ 還會與 \n 或 \r 之前的位置匹配。 |
\b | 匹配一個單詞邊界,即字與空格間的位置。 |
\B | 非單詞邊界匹配。 |
二、常用正則表達式
下面是來自菜鳥教程-正則表達式在線測試的一些常用正則表達式:
一、校驗數字的表達式
1 數字:^[0-9]*$
2 n位的數字:^\d{n}$
3 至少n位的數字:^\d{n,}$
4 m-n位的數字:^\d{m,n}$
5 零和非零開頭的數字:^(0|[1-9][0-9]*)$
6 非零開頭的最多帶兩位小數的數字:^([1-9][0-9]*)+(.[0-9]{1,2})?$
7 帶1-2位小數的正數或負數:^(\-)?\d+(\.\d{1,2})?$
8 正數、負數、和小數:^(\-|\+)?\d+(\.\d+)?$
9 有兩位小數的正實數:^[0-9]+(.[0-9]{2})?$
10 有1~3位小數的正實數:^[0-9]+(.[0-9]{1,3})?$
11 非零的正整數:^[1-9]\d*$ 或 ^([1-9][0-9]*){1,3}$ 或 ^\+?[1-9][0-9]*$
12 非零的負整數:^\-[1-9][]0-9"*$ 或 ^-[1-9]\d*$
13 非負整數:^\d+$ 或 ^[1-9]\d*|0$
14 非正整數:^-[1-9]\d*|0$ 或 ^((-\d+)|(0+))$
15 非負浮點數:^\d+(\.\d+)?$ 或 ^[1-9]\d*\.\d*|0\.\d*[1-9]\d*|0?\.0+|0$
16 非正浮點數:^((-\d+(\.\d+)?)|(0+(\.0+)?))$ 或 ^(-([1-9]\d*\.\d*|0\.\d*[1-9]\d*))|0?\.0+|0$
17 正浮點數:^[1-9]\d*\.\d*|0\.\d*[1-9]\d*$ 或 ^(([0-9]+\.[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*\.[0-9]+)|([0-9]*[1-9][0-9]*))$
18 負浮點數:^-([1-9]\d*\.\d*|0\.\d*[1-9]\d*)$ 或 ^(-(([0-9]+\.[0-9]*[1-9][0-9]*)|([0-9]*[1-9][0-9]*\.[0-9]+)|([0-9]*[1-9][0-9]*)))$
19 浮點數:^(-?\d+)(\.\d+)?$ 或 ^-?([1-9]\d*\.\d*|0\.\d*[1-9]\d*|0?\.0+|0)$
二、校驗字符的表達式
1 漢字:^[\u4e00-\u9fa5]{0,}$
2 英文和數字:^[A-Za-z0-9]+$ 或 ^[A-Za-z0-9]{4,40}$
3 長度為3-20的所有字符:^.{3,20}$
4 由26個英文字母組成的字符串:^[A-Za-z]+$
5 由26個大寫英文字母組成的字符串:^[A-Z]+$
6 由26個小寫英文字母組成的字符串:^[a-z]+$
7 由數字和26個英文字母組成的字符串:^[A-Za-z0-9]+$
8 由數字、26個英文字母或者下划線組成的字符串:^\w+$ 或 ^\w{3,20}$
9 中文、英文、數字包括下划線:^[\u4E00-\u9FA5A-Za-z0-9_]+$
10 中文、英文、數字但不包括下划線等符號:^[\u4E00-\u9FA5A-Za-z0-9]+$ 或 ^[\u4E00-\u9FA5A-Za-z0-9]{2,20}$
11 可以輸入含有^%&',;=?$\"等字符:[^%&',;=?$\x22]+
12 禁止輸入含有~的字符:[^~\x22]+
三、正則表達式實例
下面的實例均可以在菜鳥教程-正則表達式在線測試這個網址進行測試。
一、匹配前面是數字,后面是指定字母的字符串
//實例字符串
1abc //匹配
123abc //匹配
a123abc //不匹配
123abcd //不匹配
//實例正則表達式
^[0-9]+abc$
- ^ 為匹配輸入字符串的開始位置。
- [0-9]+匹配多個數字, [0-9] 匹配單個數字,+ 匹配一個或者多個。
- abc$匹配字母 abc 並以 abc 結尾,$ 為匹配輸入字符串的結束位置。
二、匹配符合"用戶注冊表單"規則的字符串
我們在寫用戶注冊表單時,只允許用戶名包含字符、數字、下划線和連接字符(-),並設置用戶名的長度,我們就可以使用以下正則表達式來設定。
//實例字符串
abc123 //匹配
123abc //匹配
_abc123 //匹配
-abc123 //匹配
ab //不匹配
ABC //不匹配
//實例正則表達式
^[a-z0-9_-]{3,15}$
- a-z 匹配小寫字母,0-9+匹配數字,_ 匹配下划線,-匹配連字符。
- {3,15}表示字符數目要求在3~15之間。
三、提取指定字符串后的數字
//實例字符串
passwd=123456
//實例正則表達式
(?!passwd=)\d+ //提取出123456
- (?!passwd=) 在任何不匹配passwd=的字符串開始處,匹配查找字符串。
- \d+ 匹配多個數字, \d 匹配數字,+ 匹配一個或者多個。
四、驗證由兩位數字、一個連字符再加 5 位數字組成的 ID 號
//實例字符串
12-34567
//實例正則表達式
\d{2}-\d{5}
- (?!passwd=) 在任何不匹配passwd=的字符串開始處,匹配查找字符串。
- \d+ 匹配多個數字, \d 匹配數字,+ 匹配一個或者多個。
四、Qt中使用正則表達式
一、限制QLineEdit只能輸入6位數字
QValidator *accountValidator = new QRegExpValidator(QRegExp("[0-9]{6}"));
ui->lineEdit->setValidator(accountValidator);
二、QString使用正則表達式
QString strOldPasswd = QString(file.readLine()).section(QRegExp("(?!passwd=)\d+"),1,1);