- 原文地址:Upcoming Regular Expression Features
- 原文做者:Jakob Gruber、Yang Guo
- 譯文出自:掘金翻譯計劃
- 本文永久連接:github.com/xitu/gold-m…
- 譯者:sunui
- 校對者:atuooo、Tina92
ES2015 給 JavaScript 語言引入了許多新特性,其中包括正則表達式語法的一些重大改進,新增了 Unicode 編碼 (/u
) 和粘滯位 (/y
)兩個修飾符。而在那以後,發展也並未中止。通過與 TC39(ECMAScript 標準委員會)的其餘成員的緊密合做,V8 團隊提議並共同設計了讓正則表達式更強大的幾個新特性。javascript
這些新特性目前已經計劃包含在 JavaScript 標準中。雖然提案尚未徹底經過,可是它們已經進入 TC39 流程的候選階段了。咱們已經以試驗功能(見下文)在瀏覽器實現了這些特性,以便在最終定稿以前提供及時的設計和實現反饋給各自的提案做者。html
本文給您預覽一下這個使人興奮的將來。若是您願意跟着體驗這些即將到來的示例,能夠在 chrome://flags/#enable-javascript-harmony
頁面中開啓實驗性 JavaScript 功能。前端
正則表達式能夠包含所謂的捕獲(或捕獲組),它能夠捕獲一部分匹配的文本。到目前爲止,開發者只能經過索引來引用這些捕獲,這取決於其在正則匹配中的位置。java
const pattern =/(\d{4})-(\d{2})-(\d{2})/u;
const result = pattern.exec('2017-07-10');
// result[0] === '2017-07-10'
// result[1] === '2017'
// result[2] === '07'
// result[3] === '10'複製代碼
但正則表達式已經因難於讀、寫和維護而臭名昭著,而且數字引用會使事情進一步複雜化。例如,在一個更長的表達式中判斷一個獨特捕獲的索引是很困難的事:react
/(?:(.)(.(?<=[^(])(.)))/ // 最後一個捕獲組的索引是?複製代碼
更糟糕的是,更改一個表達式可能會潛在地轉變全部已存在的捕獲的索引:android
/(a)(b)(c)\3\2\1/ // 一些簡單的有序的反向引用。
/(.)(a)(b)(c)\4\3\2/ // 全部都須要更新。複製代碼
命名捕獲是一個即將到來的特性,它容許開發者給捕獲組分配名稱來幫助儘量地解決這些問題。語法相似於 Perl、Java、.Net 和 Ruby:ios
const pattern =/(?<year>\d{4})-(?<month>\d{2})-(?<day>\d{2})/u;
const result = pattern.exec('2017-07-10');
// result.groups.year === '2017'
// result.groups.month === '07'
// result.groups.day === '10'複製代碼
命名捕獲組也能夠被命名的反向引用來引用,並傳入 String.prototype.replace
:git
// 命名反向引用。
/(?<LowerCaseX>x)y\k<LowerCaseX>/.test('xyx'); //true
// 字符串替換。
const pattern =/(?<fst>a)(?<snd>b)/;
'ab'.replace(pattern,'$<snd>$<fst>'); // 'ba'
'ab'.replace(pattern,(m, p1, p2, o, s,{fst, snd})=> fst + snd); // 'ba'複製代碼
關於這個新特性的所有詳情能夠在規範提案中查看。github
默認狀況下,元字符 .
在正則表達式中匹配除了換行符之外的任何字符:web
/foo.bar/u.test('foo\nbar'); // false複製代碼
一個提案引入了 dotAll 模式,經過 /s
修飾符來開啓。在 dotAll 模式中,.
也能夠匹配換行符。
/foo.bar/su.test('foo\nbar'); // true複製代碼
關於這個新特性的所有詳情能夠在規範提案中查看。
正則表達式語法已經包含了特定字符類的簡寫。\d
表明數字而且只能是 [0-9]
;\w
是單詞字符的簡寫,或者寫成 [A-Za-z0-9_]
。
自從 ES2015 引入了 Unicode,忽然間大量的字符能夠被認爲是數字,例如圈一:①;或者被認爲是字符的,例如中文字符:雪。
它們都不會被 \d
或 \w
匹配。而改變這些簡寫的含義將會破壞已經存在的正則表達式模式。
因而,新的字串類被引入。注意它們只在使用 /u
修飾符的 Unicode-aware 正則表達式中可用。
/\p{Number}/u.test('①'); // true
/\p{Alphabetic}/u.test('雪'); // true複製代碼
排除型字符可使用 \P
匹配。
/\P{Number}/u.test('①'); // false
/\P{Alphabetic}/u.test('雪'); // false複製代碼
統一碼聯盟還定義了許多方式來分類碼位,例如數學符號和日語平假名字符:
/^\p{Math}+$/u.test('∛∞∉'); // true
/^\p{Script_Extensions=Hiragana}+$/u.test('ひらがな'); // true複製代碼
所有受支持的 Unicode 屬性類列表能夠在目前的規範提案中找到。更多示例請查看這篇內容豐富的文章。
先行斷言從一開始就已是 JavaScript 正則表達式語法的一部分。與之相對的後行斷言也終於將被引入。大家中的一些人可能記得,這成爲 V8 的一部分已經有一段時間了。咱們甚至在底層已經用後行斷言實現了 ES2015 規定的 Unicode 修飾符。
「後行斷言」這個名字已經很好地描述了它的涵義。它提供一個方式來限制一個正則,只有後行組匹配經過以後才繼續匹配。它提供匹配和非匹配兩種選擇:
/(?<=\$)\d+/.exec('$1 is worth about ¥123'); // ['1']
/(?<!\$)\d+/.exec('$1 is worth about ¥123'); //['123']複製代碼
更多詳細信息,查看咱們以前的一篇博文,專門介紹了後行斷言。相關示例能夠查看V8 測試用例。
本文的完成有幸獲得了不少相關人士的幫助,他們的辛勤工做造就了這一切:特別是語言之王Mathias Bynens、Dan Ehrenberg、Claude Pache、Brian Terlson、Thomas Wood、Gorkem Yakin、和正則大師 Erik Corry;還有爲語言規範做出努力的每個人以及 V8 團隊對這些特性的實施。
但願您能像咱們同樣爲這些新的正則表達式特性而感到興奮!
掘金翻譯計劃 是一個翻譯優質互聯網技術文章的社區,文章來源爲 掘金 上的英文分享文章。內容覆蓋 Android、iOS、React、前端、後端、產品、設計 等領域,想要查看更多優質譯文請持續關注 掘金翻譯計劃。