學習正則,學習過程中發現這 6 個方便的正則表達式
幾乎所有流行的編程語言都支持正則表達式,因為正則實在是太強大了,它能讓我們原本需要數十行代碼才能完成的,正則大哥一行就能搞定了。
在本文中,我們將研究前端開發人員經常必須處理的6個文本處理和操作,并了解正則表達式是如何簡化這個過程的。
查找包含特定單詞的句子
假設我們想要匹配文本中包含特定單詞的所有句子。因為需要在搜索結果中顯示這些句子,或者想從文本中刪除它們。正則表達式/[^.!?]*\bword\b[^.!?]*.?/gi可以幫我們做到這一點。如下所示:
- const str = "The apple tree originated in Central Asia. It is cultivated worldwide. Apple matures in late summer or autumn."
- // 查找包含單詞“ apple”的句子
- str.match(/[^.!?]*\bapple\b[^.!?]*.?/gi)
- // 輸出結果
- // => ["The apple tree originated in Central Asia.", "Apple matures in late summer or autumn."]
接著,我們來看此正則表達式含義:
- [^.!?] 表示匹配任務字符,除了 ., !和?
- *匹配[^.!?]結果的 0 次或者多次
- \b 匹配單詞的邊界
- apple 就是匹配apple(因為它區分大小寫,我們在正則表達式的末尾添加i標志)
- \b 匹配單詞的邊界
- [^.!?] 表示匹配任務字符,除了 ., !和?
- *匹配[^.!?]結果的 0 次或者多次
- .匹配任何字符,除了換行
- ?匹配.所匹配到的結果的 0 次或者 1 次
- g 告訴正則表達式引擎匹配所有匹配項,而不是在第一次匹配后停止
- i 使搜索不區分大小寫
從文件名中去除無效字符
下載的文件時,其名稱中不應包含某些字符。例如,在 Windows 中,以下字符在文件名中無效,應將其刪除:
- <
- >
- :
- “
- /
- \
- |
- ?
- *
使用正則表達式,去除無效字符非常簡單。讓我們看一個例子
- const str = "https://en.wikipedia.org/"
- str.replace(/[<>|:"*?\\/]+/g, '')
- // => "httpsen.wikipedia.org"
[] 稱為字符類,JS 會把字符串與方括號之間的字符之一匹配,在配合全局(g)標志,我們可以有效地從字符串中去除方括號內的字符。
注意,在字符類中,反斜杠有特殊含義,必須用另一個反斜杠進行轉義:\\。+操作符表示重復字符類,以便同時替換一系列無效字符,這有利于提高性能。當然可以省略,對結果也沒有影響。
請記住,除非希望將無效字符替換為另一個字符,否則replace()方法的第二個參數必須為空字符串。
Windows 內部還使用了幾個保留名稱來執行各種任務,并且這些保留名稱不允許用作文件名,保留名稱如下:
CON, PRN, AUX, NUL, COM1, COM2, COM3, COM4, COM5, COM6, COM7, COM8, COM9, LPT1, LPT2, LPT3, LPT4, LPT5, LPT6, LPT7, LPT8, 和 LPT9
如果您想了解更多信息,Microsoft的Windows開發中心提供了有關有效文件名的詳盡文章。
要排除保留名稱,可以使用以下代碼:
- str.replace(/^(CON|PRN|AUX|NUL|COM1|COM2|COM3|COM4|COM5|COM6|COM7|COM8|COM9|LPT1|LPT2|LPT3|LPT4|LPT5|LPT6|LPT7|LPT8|LPT9)$/i, 'file')
上面代碼主要是將保留字替換成指定的字符。
請注意,如果字符串包含非保留字其他字符,則不會替換。例如,會把“con”替換掉,但不會替換“concord”,所以 這是有效的文件名。
其中 ,^匹配字符串的開頭。它確保沒有其他字符出現在我們要匹配的字符串之前,$則匹配字符串的結尾。
我們還可以通過使用字符類以更簡單方式來簡化該正則:
- str.replace(/^(CON|PRN|AUX|NUL|COM[1-9]|LPT[1-9])$/i, 'file')
[1–9]匹配 1 到 9 之間的數字。
用單個空格替換多個空格
當網頁渲染時,重復的空格字符被顯示為單個空格。但是,有時我們希望用戶輸入或其他數據中包含的多個空格,我們只想用用單個空格來表示。使用正則表達式可以很簡單的做到這點:
- const str = " My opinions may have changed, but not the fact that I'm right."
- str.replace(/\s\s+/g, ' ')
- // => " My opinions may have changed, but not the fact that I'm right."
此正則表達式僅包含兩個元字符,一個運算符和一個標志位:
- \s匹配單個空格字符,包括ASCII空格,制表符,換行符,回車符,垂直制表符和換頁符
- \s 再次匹配一個空格字符
- +與上一項匹配一次或多次,也就是匹配一個或多個空格
- g 告訴正則表達式引擎匹配所有匹配項,而不是在第一次匹配后停止
上面的結果是替換了至少重復兩次的所有空白字符。請注意,上面示例中的結果在開始時仍具有空白字符,應將其刪除。為此,只需將trim()函數添加到語句的末尾:
- str.replace(/\s\s+/g, ' ').trim()
- // => "My opinions may have changed, but not the fact that I'm right."
請記住,此代碼用空格(U + 0020)字符替換任何類型的空格字符,包括ASCII空格,制表符,換行符,回車符,垂直制表符和換頁符。因此,如果回車符緊跟在制表符之后,它們將被空格替換。如果這不是我們的意圖,并且只想替換相同類型的空格,請改用以下代碼:
- str.replace(/(\s)\1+/g, '$1').trim();
\1是一個反向引用,與在第一對括號(\s)中匹配的相同字符匹配。要替換它們,我們在replace()的第二個參數中使用$1,該參數將在括號中插入匹配的字符。
限制用戶只能輸入數字或字母
Web開發過程中的一項常見表單操作就是限制用戶輸入。比如,我們想將用戶限制為數字或者字母。同樣,使用正則,很簡單就能做到:使用字符類定義允許的字符范圍,然后在其后附加一個量詞以指定可以重復的字符數:
- const input1 = "John543";
- const input2 = ":-)";
- /^[A-Z0-9]+$/i.test(input1); // → true
- /^[A-Z0-9]+$/i.test(input2); // → false
運作方式如下:
- ^匹配字符串的開頭,它確保沒有其他字符出現在我們要匹配的字符串之前。
- [A-Z0–9]匹配介于A和Z之間或介于0和9之間的字符。由于這是區分大小寫的,因此我們將i標志,表示忽略大小寫。或者,我們也可以使用 [A-Za-z0–9]來代替。
- + 匹配一次或多次。因此,輸入必須至少包含一個非空白的字母數字字符;否則,匹配失敗。如果要使該字段為可選字段,則可以使用*量詞,該量詞與前面的項匹配零次或多次。
- $匹配字符串的結尾。
將網址變成鏈接
假設我們在文本中有一個或多個不是 HTML 錨元素的網址,因此無法點擊。我們希望將 URL 自動轉換為鏈接。為此,我們首先需要找到 URL,然后將每個 URL 包裹在…標記中,并使用的href屬性指向該URL:
- const str = "Visit https://en.wikipedia.org/ for more info.";
- str.replace(/\b(https?|ftp|file):\/\/\S+[\/\w]/g, '<a href="$&">$&</a>')
- // => "Visit <a href="https://en.wikipedia.org/">https://en.wikipedia.org/</a> for more info."
來看看這段代碼是如何工作的:
- \b匹配單詞邊界的位置
- (https?|ftp|file) 匹配字符https,http,ftp或file。
- : 從字面上匹配冒號
- \/ 從字面上匹配正斜杠字符
- \S 匹配任何非空格的單個字符
- + 匹配上一項一次或多次
- [\/\w] 匹配正斜杠或單詞字符。如果沒有這個,則正則表達式將匹配URL末尾的所有標點符號
- g告訴正則表達式引擎匹配所有匹配項,而不是在第一次匹配后停止
- $& 在 replace() 的第二個參數中,將匹配的子字符串插入替換字符串中
刪除重復的單詞
有時,我們會發現有的文章單詞重復了,如果通過遍歷來去重,就很麻煩。幸運的是,正則僅用一行代碼就能解決此問題:
- const str = "This this sentence has has double words."
- str.replace(/\b(\w+)\s+\1\b/gi, '$1')
- // => "This sentence has double words."
- \b 匹配單詞的邊界
- \w 匹配單詞字符
- + 匹配上一項的一次或多次
- \1 是一個反向引用,它表示在第一對括號中所匹配的文本
- \b 匹配單詞邊界
- g 告訴正則表達式引擎匹配所有匹配項,而不是在第一次匹配后停止
- i 忽略大小寫
- $1表示分組的第一個文本內容
總結
正則表達式已成為任何程序員必備的技能之一。在本文中,我們研究了前端開發人員如何利用正則表達式執行各種任務。但是,我們只是挖掘了正則表達式一些基礎面。
多花點時間來學習正則,我覺得這是很值得的,有時候我們遇到到很復雜的規則時,當你的有同事正在絞盡腦汁寫著上百行的代碼,你只用一句正則就能搞定,我相信,你的同事將對你刮目相看。加油!!!
作者:Faraz Kelhini 譯者:前端小智 來源:medium
原文:https://code.tutsplus.com/tutorials/8-regular-expressions-you-should-know--net-6149
本文轉載自微信公眾號「 大遷世界」,可以通過以下二維碼關注。轉載本文請聯系 大遷世界公眾號。