正則裡的忽略優先量詞有*?
,+?
,??
,也就是匹配優先量詞加上乙個?
,忽略優先也叫做我們平時說的惰性匹配
忽略優先量詞也是dfa
和nfa
的分水嶺,這個東西是nfa
裡特有的,dfa
裡沒有的。
忽略優先量詞與匹配優先量詞不同的地方在於,匹配優先量詞會首先嘗試匹配,而忽略優先量詞會先嘗試忽略,在儲存狀態的時候也是不一樣的,匹配優先量詞因為會先嘗試匹配,所以它的備用狀態儲存在該量詞的後面,而忽略優先量詞, 因為它會先嘗試忽略, 所以狀態儲存在該量詞的前面。
結合匹配優先量詞,來看乙個例子
假如我現在有這樣乙個字串
hello my name is "zhangsan", and my father name is "zhangsi"
如果現在我們要匹配前面引號裡面的zhangsan
我們應該怎麼做,我們好像可以直接zhangsan
,這樣,但是這只是個特例,我們的初衷是為了匹配引號中的東西。
如果我們用".*"
來匹配呢?那匹配到的結果肯定是
"zhangsan", and my father name is "zhangsi"
這是為啥?
因為*
是匹配優先的量詞啊,在進行匹配的時候,*
肯定是會先嘗試匹配,它會將整個文字都匹配完, 當控制權來到"
手上時,它交出最後乙個字元"
,此時匹配成功,所以匹配的結果是這個。
但是這不是我們想要的結果啊!那我們應該如何來匹配?答案是用忽略優先量詞".*?"
在開始匹配的時候,*?
會因為是忽略優先而放棄匹配,然後控制權交給"
,發現匹配失敗,回溯,接著匹配,以此往復,當匹配到"
時,匹配成功,匹配結果為 :
"zhangsan"
太好了!這是我們想要的結果!
我們發現,匹配優先量詞會先貪婪的把能匹配的都匹配了,然後最後再以大局為重被迫交出幾個字元,這樣看好像是從後往前來匹配的,而忽略優先量詞會懶惰的不想匹配,然後再以大局為重被迫匹配幾個字元,在這樣看好像是順序匹配的。
假如有一篇長篇大論,然而你只想匹配開頭的子串的話,你應該首先選擇忽略優先量詞
,如果你只是想匹配後面的子串,你應該首先選擇匹配優先量詞
。
不妨在看乙個比較極端的例子
function targetstringfactory()
return [originstr, ...attacharr].join("");
}let str = targetstringfactory();
console.time("greedy");
str.match(/.*[0-9]/);
console.timeend("greedy");
console.time("lazy");
str.match(/.*?[0-9]/);
console.timeend("lazy");
我只是想匹配開頭的abcd1234
,後面跟著 1000000 個 a,這時候,我們把匹配優先量詞
和忽略優先量詞
最乙個對比
greedy: 5.238ms
lazy: 0.113ms
發現忽略優先量詞
確實比匹配優先量詞
要快的多… regex 以大局為重的匹配優先量詞
在正規表示式中有三個匹配優先的量詞,分別是 所謂匹配優先,其實就是日常說的貪婪,它們會盡可能的匹配更多的字元,換一種說法,它們一般會匹配大於下限,它們好像一群好久沒吃飽飯的窮苦人民,有東西吃,當然要盡可能吃的更多啊!比如說,現在有這樣乙個字串 hello man 如果我用.去匹配,得到的將會是hel...
關於 匹配優先 和 忽略優先
color green size large 為了更好的理解 匹配優先 和 忽略優先 我們可以這樣定義 匹配優先 可以理解為 貪婪匹配 或 非懶惰匹配 忽略優先 可以理解為 非貪婪匹配 或 懶惰匹配 size color color red size large 強調一點 表示式cat不是匹配以ca...
用Regex來忽略大小替換字串
string if string.isnullorwhitespace pattern continue console.write 模式說明匹配兩個連續反斜槓 字元。因為反斜槓字元被解釋為轉義符,每個反斜槓必須由另乙個反斜槓進行轉義。environment.machinename 匹配 envir...