博客專欄

EEPW首頁(yè) > 博客 > HTML5培訓(xùn)之平衡組/遞歸匹配詳解及詳解

HTML5培訓(xùn)之平衡組/遞歸匹配詳解及詳解

發(fā)布人:only1 時(shí)間:2020-09-04 來(lái)源:工程師 發(fā)布文章

有時(shí)我們需要匹配像(100*(50+15))這樣的可嵌套的層次性結(jié)構(gòu),這時(shí)簡(jiǎn)單地使用\(.+\)則只會(huì)匹配到最左邊的左括號(hào)和最右邊的右括號(hào)之間的內(nèi)容(這里我們討論的是貪婪模式,懶惰模式也有下面的問(wèn)題)。假如原來(lái)的字符串里的左括號(hào)和右括號(hào)出現(xiàn)的次數(shù)不相等,比如(5/(3+2))),那我們的匹配結(jié)果里兩者的個(gè)數(shù)也不會(huì)相等。有沒(méi)有辦法在這樣的字符串里匹配到最長(zhǎng)的,配對(duì)的括號(hào)之間的內(nèi)容呢?  

為了避免(和\(把你的大腦徹底搞糊涂,我們還是用尖括號(hào)代替圓括號(hào)吧。現(xiàn)在我們的問(wèn)題變成了如何把xxaa>yy這樣的字符串里,最長(zhǎng)的配對(duì)的尖括號(hào)內(nèi)的內(nèi)容捕獲出來(lái)?  

這里需要用到以下的語(yǔ)法構(gòu)造:  

(?'group')把捕獲的內(nèi)容命名為group,并壓入堆棧(Stack)  

(?'-group')從堆棧上彈出最后壓入堆棧的名為group的捕獲內(nèi)容,如果堆棧本來(lái)為空,則本分組的匹配失敗  

(?(group)yes|no)如果堆棧上存在以名為group的捕獲內(nèi)容的話,繼續(xù)匹配yes部分的表達(dá)式,否則繼續(xù)匹配no部分  

(?!)零寬負(fù)向先行斷言,由于沒(méi)有后綴表達(dá)式,試圖匹配總是失敗  

如果你不是一個(gè)程序員(或者你自稱程序員但是不知道堆棧是什么東西),你就這樣理解上面的三種語(yǔ)法吧:第一個(gè)就是在黑板上寫一個(gè)"group",第二個(gè)就是從黑板上擦掉一個(gè)"group",第三個(gè)就是看黑板上寫的還有沒(méi)有"group",如果有就繼續(xù)匹配yes部分,否則就匹配no部分。我們需要做的是每碰到了左括號(hào),就在壓入一個(gè)"Open",每碰到一個(gè)右括號(hào),就彈出一個(gè),到了最后就看看堆棧是否為空--如果不為空那就證明左括號(hào)比右括號(hào)多,那匹配就應(yīng)該失敗。正則表達(dá)式引擎會(huì)進(jìn)行回溯(放棄最前面或最后面的一些字符),盡量使整個(gè)表達(dá)式得到匹配。  

<#最外層的左括號(hào)  

[^<>]*#最外層的左括號(hào)后面的不是括號(hào)的內(nèi)容  

(  

(  

(?'Open'<)#碰到了左括號(hào),在黑板上寫一個(gè)"Open"  

[^<>]*#匹配左括號(hào)后面的不是括號(hào)的內(nèi)容  

)+  

(  

(?'-Open'>)#碰到了右括號(hào),擦掉一個(gè)"Open"  

[^<>]*#匹配右括號(hào)后面不是括號(hào)的內(nèi)容  

)+  

)*  

(?(Open)(?!))#在遇到最外層的右括號(hào)前面,判斷黑板上還有沒(méi)有沒(méi)擦掉的"Open";如果還有,則匹配失敗  

>#最外層的右括號(hào)  

平衡組的一個(gè)最常見的應(yīng)用就是匹配HTML,下面這個(gè)例子可以匹配嵌套的標(biāo)簽:]*>[^<>]*(((?'Open']*>)[^<>]*)+((?'-Open')[^<>]*)+)*(?(Open)(?!))  

上邊已經(jīng)描述了構(gòu)造正則表達(dá)式的大量元素,但是還有很多沒(méi)有提到的東西。下面是一些未提到的元素的列表,包含語(yǔ)法和簡(jiǎn)單的說(shuō)明。你可以在網(wǎng)上找到更詳細(xì)的參考資料來(lái)學(xué)習(xí)它們--當(dāng)你需要用到它們的時(shí)候。如果你安裝了MSDNLibrary,你也可以在里面找到.net下正則表達(dá)式詳細(xì)的文檔。這里的介紹很簡(jiǎn)略,如果你需要更詳細(xì)的信息,而又沒(méi)有在電腦上安裝MSDNLibrary,可以查看關(guān)于正則表達(dá)式語(yǔ)言元素的MSDN在線文檔。  

\a報(bào)警字符(打印它的效果是電腦嘀一聲)  

\b通常是單詞分界位置,但如果在字符類里使用代表退格  

\t制表符,Tab  

\r回車  

\v豎向制表符  

\f換頁(yè)符  

\n換行符  

\eEscape  

\0nnASCII代碼中八進(jìn)制代碼為nn的字符  

\xnnASCII代碼中十六進(jìn)制代碼為nn的字符  

\unnnnUnicode代碼中十六進(jìn)制代碼為nnnn的字符  

\cNASCII控制字符。比如\cC代表Ctrl+C  

\A字符串開頭(類似^,但不受處理多行選項(xiàng)的影響)  

\Z字符串結(jié)尾或行尾(不受處理多行選項(xiàng)的影響)  

\z字符串結(jié)尾(類似$,但不受處理多行選項(xiàng)的影響)  

\G當(dāng)前搜索的開頭  

\p{name}Unicode中命名為name的字符類,例如\p{IsGreek}  

(?>exp)貪婪子表達(dá)式  

(?-exp)平衡組  

(?im-nsx:exp)在子表達(dá)式exp中改變處理選項(xiàng)  

(?im-nsx)為表達(dá)式后面的部分改變處理選項(xiàng)  

(?(exp)yes|no)把exp當(dāng)作零寬正向先行斷言,如果在這個(gè)位置能匹配,使用yes作為此組的表達(dá)式;否則使用no  

(?(exp)yes)同上,只是使用空表達(dá)式作為no  

(?(name)yes|no)如果命名為name的組捕獲到了內(nèi)容,使用yes作為表達(dá)式;否則使用no  

(?(name)yes)同上,只是使用空表達(dá)式作為no  

以上就是關(guān)于扣丁學(xué)堂HTML5培訓(xùn)之平衡組和遞歸匹配的詳細(xì)介紹,最后想要工作不累就要不斷的提升自己的技能,想要快速學(xué)習(xí)HTML5培訓(xùn)技能到扣丁學(xué)堂學(xué)習(xí)吧??鄱W(xué)堂還有名師錄制的HTML5視頻教程供學(xué)員觀看學(xué)習(xí),想要HTML5培訓(xùn)視頻教程的小伙伴快咨詢我們的專業(yè)老師索要吧??鄱W(xué)堂H5技術(shù)交流群:751662650。


*博客內(nèi)容為網(wǎng)友個(gè)人發(fā)布,僅代表博主個(gè)人觀點(diǎn),如有侵權(quán)請(qǐng)聯(lián)系工作人員刪除。



關(guān)鍵詞:

相關(guān)推薦

技術(shù)專區(qū)

關(guān)閉