Regex文法
一個Regex就是由一般字元(例如字元a 到z)以及特殊字元(稱為元字元)組成的文字模式。該模式描述在尋找文字主體時待匹配的一個或多個字串。Regex作為一個模板,將某個字元模式與所搜尋的字串進行匹配。
下表是元字元及其在Regex上下文中的行為的一個完整參考列表:
| 字元 |
描述 |
| \ |
逸出字元,在之前,我們在字串也用過這字元,即一些字元具有特殊含義,對其進行轉義使它成為一般字元,而用在一般字元上又表示其有特殊含義 |
| ^ |
匹配輸入字串的開始位置,如果設定了匹配多行(m),那麼也匹配行的開頭 |
| $ |
匹配輸入字串的結束位置。如果設定了匹配多行(m),那麼也匹配行的結束 |
| * |
匹配前面的子運算式零次或多次。例如,zo* 能匹配"z" 以及"zoo"。* 等價於{0,}。 |
| + |
匹配前面的子運算式一次或多次。例如,'zo+' 能匹配"zo" 以及"zoo",但不能匹配"z"。+ 等價於 {1,}。 |
| ? |
匹配前面的子運算式零次或一次。例如,"do(es)?" 可以匹配"do" 或"does" 中的"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?'。請注意在逗號和兩個數之間不能有空格。 |
| ? |
當該字元緊跟在任何一個其他限制符(*, +, ?, {n}, {n,}, {n,m}) 後面時,匹配模式是非貪婪的。非貪婪模式儘可能少的匹配所搜尋的字串,而預設的貪婪模式則儘可能多的匹配所搜尋的字串。例如,對於字串"oooo",'o+?' 將匹配單個"o",而'o+' 將匹配所有'o'。 |
| . |
匹配除"\n" 之外的任何單個字元。要匹配包括'\n' 在內的任何字元,請使用象'[.\n]' 的模式。 |
| (pattern) |
匹配pattern並擷取這一匹配。所擷取的匹配可以從產生的Matches 集合得到,使用$0…$9屬性。要匹配圓括弧字元,請使用'\(' 或 '\)'。 |
| (?:pattern) |
匹配pattern但不擷取匹配結果,也就是說這是一個非擷取匹配,不進行儲存供以後使用。這在使用"或" 字元 (|) 來組合一個模式的各個部分是很有用。例如,'industr(?:y|ies) 就是一個比'industry|industries' 更簡略的運算式。 |
| (?=pattern) |
正向預查,在任何匹配pattern的字串開始處匹配尋找字串。這是一個非擷取匹配,也就是說,該匹配不需要擷取供以後使用。例如,'Windows (?=95|98|NT|2000)' 能匹配 "Windows 2000" 中的"Windows" ,但不能匹配"Windows 3.1" 中的 "Windows"。預查不消耗字元,也就是說,在一個匹配發生後,在最後一次匹配之後立即開始下一次匹配的搜尋,而不是從包含預查的字元之後開始。 |
| (?!pattern) |
負向預查,在任何不匹配pattern的字串開始處匹配尋找字串。這是一個非擷取匹配,也就是說,該匹配不需要擷取供以後使用。例如'Windows (?!95|98|NT|2000)' 能匹配 "Windows 3.1" 中的"Windows",但不能匹配"Windows 2000" 中的 "Windows"。預查不消耗字元,也就是說,在一個匹配發生後,在最後一次匹配之後立即開始下一次匹配的搜尋,而不是從包含預查的字元之後開始 |
| x|y |
匹配x或y。例如,'z|food' 能匹配"z" 或"food"。'(z|f)ood' 則匹配"zood" 或"food"。 |
| [xyz] |
字元集合。匹配所包含的任意一個字元。例如,'[abc]' 可以匹配"plain" 中的'a'。 |
| [^xyz] |
負值字元集合。匹配未包含的任一字元。例如,'[^abc]' 可以匹配"plain" 中的'p'。 |
| [a-z] |
字元範圍。匹配指定範圍內的任一字元。例如,'[a-z]' 可以匹配'a' 到'z' 範圍內的任意小寫字母字元。 |
| [^a-z] |
負值字元範圍。匹配任何不在指定範圍內的任一字元。例如,'[^a-z]' 可以匹配任何不在'a' 到'z' 範圍內的任一字元。 |
| \b |
匹配一個單詞邊界,也就是指單詞和空格間的位置。例如,'er\b' 可以匹配"never" 中的'er',但不能匹配 "verb" 中的'er'。 |
| \B |
匹配非單詞邊界。'er\B' 能匹配"verb" 中的'er',但不能匹配"never" 中的 'er'。 |
| \cx |
匹配由x指明的控制字元。例如,\cM 匹配一個Control-M 或斷行符號符。x的值必須為 A-Z 或a-z 之一。否則,將c 視為一個原義的'c' 字元。 |
| \d |
匹配一個數字字元。等價於[0-9]。 |
| \D |
匹配一個非數字字元。等價於[^0-9]。 |
| \f |
匹配一個換頁符。等價於\x0c 和\cL。 |
| \n |
匹配一個分行符號。等價於\x0a 和\cJ。 |
| \r |
匹配一個斷行符號符。等價於\x0d 和\cM。 |
| \s |
匹配任何空白字元,包括空格、定位字元、換頁符等等。等價於[?\f\n\r\t\v]。 |
| \S |
匹配任何非空白字元。等價於[^?\f\n\r\t\v]。 |
| \t |
匹配一個定位字元。等價於\x09 和\cI。 |
| \v |
匹配一個垂直定位字元。等價於\x0b 和\cK。 |
| \w |
匹配包括底線的任何單詞字元。等價於'[A-Za-z0-9_]'。 |
| \W |
匹配任何非單詞字元。等價於'[^A-Za-z0-9_]'。 |
| \xn |
匹配n,其中n為十六進位轉義值。十六進位轉義值必須為確定的兩個數字長。例如,'\x41' 匹配"A"。'\x041' 則等價於'\x04' & "1"。Regex中可以使用ASCII 編碼。. |
| \num |
匹配num,其中num是一個正整數。對所擷取的匹配的引用。例如,'(.)\1' 匹配兩個連續的相同字元。 |
| \n |
標識一個八進位轉義值或一個後向引用。如果\n之前至少n個擷取的子運算式,則n為後向引用。否則,如果n為八位元字(0-7),則n為一個八進位轉義值。 |
| \nm |
標識一個八進位轉義值或一個後向引用。如果\nm之前至少有is preceded by at least nm個擷取得子運算式,則nm為後向引用。如果\nm之前至少有n個擷取,則n為一個後跟文字m 的後向引用。如果前面的條件都不滿足,若? n和m均為八位元字(0-7),則 \nm將匹配八進位轉義值nm。 |
| \nml |
如果n為八位元字(0-3),且m和l均為八位元字 (0-7),則匹配八進位轉義值nml。 |
| \un |
匹配n,其中n是一個用四個十六進位數字表示的Unicode 字元。例如,\u00A9 匹配著作權符號(?)。 |
建立Regex
var re1=new RegExp("a");
var re2=/\d{2}/;
alert(re1.test("a"));//true
alert(re2.test("wa12le"));//true
RegExp建構函式第一個參數為Regex的常值內容,而第一個參數則為可選項標誌.標誌可以組合使用
g (全文尋找)
i (忽略大小寫)
m (多行尋找)
var re1=new RegExp("a","i");
和Regex相關的方法和屬性
Regex對象的方法
• test,返回一個 Boolean 值,它指出在被尋找的字串中是否存在模式。如果存在則返回 true,否則就返回 false。
• exec,用Regex模式在字串中運行尋找,並返回包含該尋找結果的一個數組。
• compile,把Regex編譯為內部格式,從而執行得更快。//這個目前很少用,Google瀏覽器支援有問題
測試Regex的具體用法:
上面的test方法僅僅知道了字串是否匹配模式,如果我們需要知道哪些字元匹配了模式怎麼辦?
exec返回的數組第1到n元素中包含的是匹配中出現的任意一個子匹配
1 var version="XunLei.China 2012";
2 var re=/^[a-z]+\.+[a-z]+\s+\d+$/i;
3 alert(re.test(version));//true 匹配成功
4 //問題是怎麼知道版本號碼的資訊,使用exec
5 alert(re.exec(version));//由於此時沒有捕獲值所以直接返回XunLei.China 2012
6 //這樣我們只需要給版本號碼加個()用於儲存捕獲
7 var re1=/^[a-z]+\.+[a-z]+\s+(\d+)$/i;
8 var verArr=re1.exec(version);
9 alert(verArr[0]);//全部資訊
10 alert(verArr[1]);//版本號碼
11 //簡單的方法是重新定義一個正則式直接擷取數字部分
12 var re2=/\d+/;
13 alert(re2.exec(version));//返回2012
消除行號
此外:當字串不匹配re時,exec方法將返回null。
String對象一些和Regex相關的方法
match,找到一個或多個Regex的匹配。
replace,替換與Regex匹配的子串。
search,檢索與Regex相匹配的值。
split,把字串分割為字串數組。
1 var str="Hello Rohelm!";
2 alert(str.replace("Rohelm","everyone"));//返回Hello everyone.
3 //上面使我們平時用的方法,當然我們可以聯想到C#中正則類的字串操作方法
4 //replace的第一個參數可以為Regex
5 var re=/\s+/;//空白字元 www.2cto.com
6 //在不知道字串中有多少空白字元時,Regex極為方便
7 alert(str.replace(re,"^_×"));
8 var str = "2012-12-25";
9 var arr = str.split("-");//返回["2012","12","25"]
10 alert(arr[0]+"年"+arr[1]+"月"+arr[2]+"日");
11 //我們可以這樣擷取時間,但是使用者可能任意的輸入例如2012 2 21或者2012 —2 21
12 var re1=/[^0-9]+/;//用來匹配使用者無法預知的輸入補白
13 var str1="2012+2%21";
14 var arr1=str1.split(re1);//按照Regex指定的規則分割字串
15 alert(arr1[0]+"年"+arr1[1]+"月"+arr1[2]+"日");
16 //在字串中尋找時我們常用indexOf,與之對應用於正則尋找的方法是search
17 str2 = "萬盛區集體大暴亂啊,重慶的孩子傷不起啊,傷不起!";//年齡不是一定的,我們用indexOf不能尋找它的位置
18 re2 = /傷不起/;
19 alert(str2.search(re2));//返回尋找到的字串開始下標15
20 re3 = /傷不起/g;//我們加個全域標識發現其依然只匹配第一次出現的位置
21 //怎麼去全域搜尋呢?lastIndex
22 alert(str2.search(re3));//返回尋找到的字串開始下標15
23 //當search方法沒有找到匹配時,將返回-1
24 //類似於exec方法,String對象的match方法也用於將字串與Regex進行匹配並返回結果數組
25 //注意下.net中的Match和MatchCollection的不同,不過這裡也差不多啦
26 var str4 = "I deeply LOVE my country and people!";
27 var re4=/[A-Z]/;//匹配所有的大寫字母
28 alert(str4.match(re4));//這樣只是或返回I
29 var re5=/[A-Z]/g;//匹配所有的大寫字母
30 alert(str4.match(re5));//這樣返回["I","L","O","Y"]
31 //從字串中抽取單詞
32 re = /\b[a-z]\b/i;//\b表示單詞邊界
33 str = "one two three four";
34 alert(str.match(re));//one,two,three,four
35 </script>
RegExp對象執行個體的一些屬性
var re = /[a-z]/i;
alert(re.source);//將[a-z]字串輸出
//請注意,直接alert(re)會將Regex連同前向斜線與標誌輸出,這是re.toString方法定義的
var re1=new RegExp("[a-z]","i");
alert(re1.source);//將[a-z]字串輸出
每個RegExp對象的執行個體具有lastIndex屬性,它是被尋找字串中下一次成功匹配的開始位置,預設值是-1。
var re=/[a-z]/ig;
var str="Hello World!";
alert(re.test(str));
alert(re.lastIndex);//1
alert(re.test(str));
alert(re.lastIndex);//2
alert(re.test(str));
alert(re.lastIndex);//3
alert(re.test(str));
alert(re.lastIndex);//4
var re1=/[a-z]/ig;
var str1="Hello World!";
var arr=re1.exec(str1);
alert(re1.lastIndex);//1
var arr=re1.exec(str1);
alert(re1.lastIndex);//2
lastIndex 屬性被 RegExp 對象的 exec 和 test 方法修改.並且它是可寫的.當匹配失敗(後面沒有匹配),或lastIndex值大於字串長度時,再執行exec等方法會將lastIndex設為0(開始位置)。
RegExp對象的靜態屬性
source,返回Regex模式的文本的複本。唯讀。
lastIndex,返回字元位置,它是被尋找字串中下一次成功匹配的開始位置。
$1...$9,返回九個在模式比對期間找到的、最近儲存的部分。唯讀。
input ($_),返回執行規範表述尋找的字串。唯讀。
lastMatch ($&),返回任何Regex搜尋過程中的最後匹配的字元。唯讀。
lastParen ($+),如果有的話,返回任何Regex尋找過程中最後括的子匹配。唯讀。
leftContext ($`),返回被尋找的字串中從字串開始位置到最後匹配之前的位置之間的字元。唯讀。
rightContext ($'),返回被搜尋的字串中從最後一個匹配位置開始到字串結尾之間的字元。唯讀。
//input 用於最後匹配的字串(傳遞給test,exec方法的字串)
var re = /[A-Z]/;
var str = "Hello,World!!!";
var arr = re.exec(str);
alert(RegExp.input);//Hello,World!!!
re.exec("asd");//因為tempstr不匹配
alert(RegExp.input);//仍然是Hello,World!!!
var re1=/\d/;
var str1="2012的春天";
var b=re1.test(str1);
alert(RegExp.input);//"2012的春天"
var c=re1.test("two birds on the tree make love every day!")
alert(RegExp.input);//仍然是"2012的春天"
//lastMatch 最後匹配的字元
re = /[a-z]/g;
str = "love";
re.test(str);
alert(RegExp.lastMatch);//l
re.test(str);
alert(RegExp["$&"]);//o ,$&是lastMatch的短名字,但由於它不是合法變數名,所以要。。
//lastParen 最後匹配的分組
re = /[a-z](\d+)/gi;
str = "Class1 Class2 Class3";
re.test(str);
alert(RegExp.lastParen);//1
re.test(str);
alert(RegExp["$+"]);//2
//leftContext 返回被尋找的字串中從字串開始位置到最後匹配之前的位置之間的字元
//rigthContext 返回被搜尋的字串中從最後一個匹配位置開始到字串結尾之間的字元
re = /[A-Z]/g;
str = "123ABC456";
re.test(str);//A
alert(RegExp.leftContext);//123
alert(RegExp.rightContext);//BC456
re.test(str);//B
alert(RegExp["$`"]);//123A
alert(RegExp["$'"]);//C456
作者 謝舸哥