《正則表達式經典實例(第2版)》——2.19 在替代文本中添加字麵文本
本節書摘來自異步社區《正則表達式經典實例(第2版)》一書中的第2章,第2.19節,作者: 【美】Jan Goyvaerts , Steven Levithan著,更多章節內容可以訪問雲棲社區“異步社區”公眾號查看
2.19 在替代文本中添加字麵文本
問題描述
查找並把任何正則表達式匹配從字麵上替換為這8個字符:$%*$1\1。
解決方案
$%\*$$1\1
替代文本流派:.NET、JavaScript
\$%\\*\$1\\1
替代文本流派:Java
$%\*\$1\\1
替代文本流派:PHP
\$%\*\$1\\1
替代文本流派:Perl
$%\*$1\\1
替代文本流派:Python、Ruby
討論
在替代文本中轉義字符的時機和方式
這個實例顯示了各種替代文本流派中使用的不同轉義規則。在替代文本中,你可能會需要轉義的兩個字符是美元符號($)和反斜杠(\)。而它們所使用的轉義字符也分別是美元符號和反斜杠。
在這個例子中的百分號(%)和星號(*)總是字麵字符,然而一個前導的反斜杠也可能會被當作一個轉義字符,而不是一個字麵上的反斜杠。«$1»和/或«\1»是指向一個捕獲分組的反向引用。實例2.21中會講解哪些流派對於反向引用會使用哪種語法。這個題目對於我們講到的7種替代文本流派就存在了5種解決方案,這個事實也說明,關於替代文本的語法,根本就沒什麼標準。
.NET和JavaScript
.NET和JavaScript總是把反斜杠當作一個字麵字符。不需要再用另外一個反斜杠來對它進行轉義,否則就會在替換中得到兩個反斜杠。
單個出現的美元符號也是一個字麵字符。隻有當它們之後是數字、&、反引號、垂直引號、下劃線、加號或者另外一個美元符號的時候,才需要被轉義。要轉義美元符號,需要在它前麵再加一個美元符號。
如果你覺得這樣會讀起來更加清晰,也可以選擇把所有的美元符號都用兩個來表示。下麵這個解答也是同樣正確的:
$$%\*$$1\1
替代文本流派:.NET、JavaScript
.NET和XregExp還要求對後麵跟著一個起始花括號的美元符號進行轉義。在.NET中,«${group}»是一個命名反向引用。標準JavaScript中沒有使用XRegExp庫時則不支持命名反向引用。
Java
在Java中,反斜杠用來在替代文本中轉義反斜杠和美元符號。所有字麵的反斜杠和所有字麵的美元符號都必須轉義。如果你不轉義它們,Java就會拋出一個異常。
PHP
PHP要求後麵跟數字的反斜杠、後麵跟數字或者起始花括號的美元符號,都需要使用反斜杠來進行轉義。
反斜杠也可以對另外一個反斜杠進行轉義。因此,你需要使用«\»來在替換文本中表示兩個字麵上的反斜杠。所有其他的反斜杠都被認為是字麵上的反斜杠。
Perl
Perl與其他替代文本流派都有些不同:它其實不能歸屬到任何一種替代文本流派。雖然其他編程語言都在查找和替換過程中使用一些特殊邏輯進行替換,比如«$1»,然而Perl中這隻是正常的變量插值(interpolation)。在替代文本中,需要對所有字麵上的美元符號用反斜杠進行轉義,就像在任意雙引號字符串中一樣。
一個例外是Perl同樣支持反向引用的«\1»語法。因此,如果你需要字麵上的反斜杠後跟數字,則需要對反斜杠進行轉義。為了避免反斜杠對美元符號進行轉義,因此需要對後麵跟著美元符號的反斜杠進行轉義。
反斜杠也可以轉義另外一個反斜杠。因此,你需要使用«\»來在替換文本中表示兩個字麵上的反斜杠。所有其他的反斜杠都視為字麵上的反斜杠。
Python和Ruby
美元符號在Python和Ruby的替代文本中並不擁有特殊含義。如果反斜杠後麵跟著一個會給反斜杠賦予特殊含義的字符,那麼這個反斜杠就需要使用另外一個反斜杠進行轉義。
在Python中,«\1»~«\9»,以及«\g<»會創建反向引用。因此這些反斜杠就需要進行轉義。
在Ruby中,你需要對後麵跟著數字、&、反引號、垂直引號或者加號的反斜杠進行轉義。
在這兩種語言中,反斜杠都可以轉義另外一個反斜杠。因此,你需要使用«\»在替換文本中表示兩個字麵上的反斜杠。所有其他的反斜杠都視為字麵上的反斜杠。
更多關於字符串字麵量的轉義規則
記住在本章中,我們關心的隻是正則表達式和替代文本自身。下一章會講解編程語言和字符串字麵量的內容。
上述替代文本作為實際字符串變量直接傳遞給replace()函數是可以正常工作的。換句話說,如果你在應用程序中給用戶提供一個文本框,讓用戶輸入替代文本,那麼這些解決方案所給出的文本,正是用戶為了讓查找和替換正常工作所需要輸入的內容。如果你使用RegexBuddy或者另外一個正則測試工具來測試查找和替換命令,那麼在這個實例中給出的替代文本也同樣會給出所期望的結果。
但是如果你把它們直接粘貼到源代碼中,在兩邊放上引號字符,那麼這些同樣的替代文本並不能正常使用。編程語言中的字符串文本擁有它們自己的轉義規則,因此你需要在替代文本的轉義規則之上再遵循這些轉義規則才行。最終你所得到的很可能會是一堆混雜的反斜杠。
最後更新:2017-06-02 19:35:57