JS冷知識(shí)之不起眼但有用的String.raw方法
String.raw
String.raw
是JavaScript中模板字符串的一個(gè)標(biāo)簽函數(shù),它的作用是將模板字符串不轉(zhuǎn)義的原始字符串內(nèi)容返回。
也就是說(shuō),如下代碼:
console.log(String.raw`Hi!\nAkira`);
將直接返回字符串 Hi!\nAkira
,而不是在Hi!
和Akira
中間插入回車。因?yàn)镾tring.raw標(biāo)簽存在,所以\n
不被轉(zhuǎn)義。這樣其實(shí)相當(dāng)于如下代碼:
console.log(`Hi!\\nAkira`);
原始字符串不轉(zhuǎn)義,在某些情況下很有用。不知道大家有沒(méi)有遇到過(guò)用new RegExp
動(dòng)態(tài)構(gòu)建正則表達(dá)式的場(chǎng)景,比如下面的代碼構(gòu)建一個(gè)瀏覽器默認(rèn)塊級(jí)元素標(biāo)簽的正則匹配:
const blockTags = 'address|article|aside|base|basefont|blockquote|body|caption' + '|center|col|colgroup|dd|details|dialog|dir|div|dl|dt|fieldset|figcaption' + '|figure|footer|form|frame|frameset|h[1-6]|head|header|hr|html|iframe' + '|legend|li|link|main|menu|menuitem|meta|nav|noframes|ol|optgroup|option' + '|p|param|section|source|summary|table|tbody|td|tfoot|th|thead|title|tr' + '|track|ul'; const blockReg = new RegExp(`(<\\s*(?:(?:\\/\\s*(?:${blockTags})\\s*)|(?:(?:${blockTags})\\s*\\/\\s*)|hr)>\\s*?)\\n`, 'ig');
在這里,因?yàn)槲覀兪褂昧?code>new RegExp動(dòng)態(tài)構(gòu)建,所以我們就要把\s
替換成\\s
,把\/
替換成\\/
,把\n
替換成\\n
。但如果使用String.raw
,就可以不用這么替換,可以直接寫(xiě)成:
const blockReg = new RegExp(String.raw`(<\s*(?:(?:\/\s*(?:${blockTags})\s*)|(?:(?:${blockTags})\s*\/\s*)|hr)>\s*?)\n`, 'ig');
除了動(dòng)態(tài)構(gòu)建正則,還有輸出或執(zhí)行代碼塊的場(chǎng)景,比如:
const script = ` console.log('test \n test'); ` execScript(script);
上面這段代碼執(zhí)行會(huì)出錯(cuò),因?yàn)?code>\n在字符串字面量中被替換成換行,導(dǎo)致實(shí)際執(zhí)行的代碼變成下面這樣:
console.log('test test');
因?yàn)閱我?hào)字符串里面不能插入換行,所以上面的代碼執(zhí)行就報(bào)錯(cuò)了。
解決的辦法是:
const script = String.raw` console.log('test \n test'); ` execScript(script);
這樣就可以避免字符串代碼的轉(zhuǎn)義內(nèi)容被解析。
所以,從上面可以看出,在字符串解析的場(chǎng)景下,String.raw
就會(huì)有用。比如我們要寫(xiě)一個(gè)使用KaTeX解析公式的React組件,我們希望這么使用:
<Katex macros={{...}}> 公式字符串 </Katex>
具體實(shí)現(xiàn)我們可以這樣寫(xiě):
import katex from 'katex'; import React from 'react'; import ReactDOM from 'react-dom'; const Katex = ({children, ...props}) => { const code = katex.renderToString(children, { ...props, throwOnError: false }) return ( <span dangerouslySetInnerHTML={{__html: code}}/> ) }
對(duì)于單行公式的解析沒(méi)有問(wèn)題
<Katex>x^2+y^2=1</Katex>
能夠正確解析成:x2+y2=1x^2+y^2=1x2+y2=1
但是如果是多行公式:
<Katex macros={{"\\f": "#1f(#2)"}}> % \f is defined as #1f(#2) using the macro \f\relax{x} = \int_{-\infty}^\infty \f\hat\xi\,e^{2 \pi i \xi x} \,d\xi </Katex>
這么寫(xiě)是不行的,因?yàn)镽eact在解析JSX的時(shí)候,會(huì)把內(nèi)容中的回車去掉,空格合并,就像瀏覽器解析HTML標(biāo)簽?zāi)菢樱乙膊荒苷_處理轉(zhuǎn)義符。所以如果像上面這么寫(xiě),最后瀏覽器會(huì)報(bào)錯(cuò)。
這時(shí)候,我們就可以使用String.raw標(biāo)簽,將上面的代碼寫(xiě)成下面這樣:
<Katex macros={{"\\f": "#1f(#2)"}}>{String.raw` % \f is defined as #1f(#2) using the macro \f\relax{x} = \int_{-\infty}^\infty \f\hat\xi\,e^{2 \pi i \xi x} \,d\xi `}</Katex>
這樣KaTeX就能正確解析字符串內(nèi)容了,最終實(shí)現(xiàn)效果如下:
https://code.juejin.cn/pen/7106683225786810376
自定義標(biāo)簽
除了默認(rèn)的String.raw,我們自定義的標(biāo)簽函數(shù),也可以通過(guò)strings.raw來(lái)獲得原始字符串內(nèi)容,所以我們也可以將KaTeX公式解析定義成標(biāo)簽函數(shù):
function KaTeX(strings, macros) { return katex.renderToString(strings.raw.join(''), { macros, throwOnError: false }); }
這樣我們就可以通過(guò)標(biāo)簽函數(shù)來(lái)解析公式,再用React渲染出來(lái):
https://code.juejin.cn/pen/7106726810817462286
以上就是全部?jī)?nèi)容,雖然很簡(jiǎn)單,但是非常有用。
你還知道或用過(guò)String.raw
以及其他標(biāo)簽函數(shù)嗎?歡迎在評(píng)論區(qū)討論。
到此這篇關(guān)于JS冷知識(shí)不起眼但有用的String.raw方法的文章就介紹到這了,更多相關(guān)javascript string.raw方法內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
javascript HTMLEncode HTMLDecode的完整實(shí)例(兼容ie和火狐)
用的瀏覽器內(nèi)部轉(zhuǎn)換器實(shí)現(xiàn)轉(zhuǎn)換,方法是動(dòng)態(tài)創(chuàng)建一個(gè)容器標(biāo)簽元素2009-06-06js+css3實(shí)現(xiàn)旋轉(zhuǎn)效果
本文主要介紹了js+css3實(shí)現(xiàn)旋轉(zhuǎn)效果的方法。具有一定的參考價(jià)值,下面跟著小編一起來(lái)看下吧2017-01-01獲取今天,昨天,本周,上周,本月,上月時(shí)間(實(shí)例分享)
本篇文章主要分享了獲取今天,昨天,本周,上周,本月,上月時(shí)間實(shí)例代碼,具有一定的參考價(jià)值,下面跟著小編一起來(lái)看下吧2017-01-01JavaScript如何將數(shù)據(jù)處理成樹(shù)形結(jié)構(gòu)
這篇文章主要介紹了JavaScript如何將數(shù)據(jù)處理成樹(shù)形結(jié)構(gòu)問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-06-06Canvas 制作動(dòng)態(tài)進(jìn)度加載水球詳解及實(shí)例代碼
這篇文章主要介紹了Canvas 制作動(dòng)態(tài)進(jìn)度加載水球詳解及實(shí)例代碼的相關(guān)資料,這里附有實(shí)例代碼及實(shí)現(xiàn)效果圖,需要的朋友可以參考下2016-12-12JavaScript利用正則表達(dá)式替換字符串中的內(nèi)容
本文主要介紹了JavaScript利用正則表達(dá)式替換字符串中內(nèi)容的具體實(shí)現(xiàn)方法,并做了簡(jiǎn)要注釋,便于理解。具有一定的參考價(jià)值,需要的朋友可以看下2016-12-12識(shí)別操作系統(tǒng)是不是vista的js代碼
識(shí)別操作系統(tǒng)是不是vista的js代碼...2007-08-08IE8中動(dòng)態(tài)創(chuàng)建script標(biāo)簽onload無(wú)效的解決方法
這篇文章主要介紹了IE8中動(dòng)態(tài)創(chuàng)建script標(biāo)簽onload無(wú)效的解決方法,涉及針對(duì)javascript加載順序的調(diào)整,具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2014-12-12JS實(shí)現(xiàn)的tab切換并顯示相應(yīng)內(nèi)容模塊功能示例
這篇文章主要介紹了JS實(shí)現(xiàn)的tab切換并顯示相應(yīng)內(nèi)容模塊功能,結(jié)合實(shí)例形式分析了JavaScript基于事件響應(yīng)、元素遍歷實(shí)現(xiàn)頁(yè)面tab切換功能相關(guān)操作技巧,需要的朋友可以參考下2019-08-08js實(shí)現(xiàn)增加數(shù)字顯示的環(huán)形進(jìn)度條效果
本文主要分享了js實(shí)現(xiàn)增加數(shù)字顯示的環(huán)形進(jìn)度條效果的示例代碼。具有一定的參考價(jià)值,下面跟著小編一起來(lái)看下吧2017-02-02