出來混總是要還的-JS正則前傳
前言: 正則表示式一直是個人痛點, 相信很多人 (說的就是你 ) 跟我一樣存在類似的情況, 正則是反覆學, 反覆忘, 從個人角度看主要的原因還是:較少的使用場景, 如果像陣列的幾個常用方法一樣, 絕大多數人肯定能熟練運用。 最近迫使我拿起正則這把屠龍刀的起因是( 時間充足和一道小的面試題 ), 那咱們就先從這道面試題說起
Demo1
// 觀察如下規律, 寫一個函式`accum` // accum("abcd");// "A-Bb-Ccc-Dddd" // accum("helloWorld");// "H-Ee-Lll-Llll-Ooooo-Wwwwww-Ooooooo-Rrrrrrrr-Lllllllll-Dddddddddd" // accum("China");// "C-Hh-Iii-Nnnn-Aaaaa" 複製程式碼
看到題的第一反應就是, 握草這還不簡單, 兩層迴圈加上珍藏多年的字串拼接技術(-_-||), 妥妥的解決這個問題
const accum = str => { let result = ""; str.toLowerCase().split("").forEach((el, idx) => { for (let i = 0; i <= idx; i++) { if (i == 0) { result += el.toUpperCase(); } else { result += el; } } result += el + "-"; }); return result.slice(0, -1); // 看到slice慌不慌?是不是忘記這鬼東西是幹什麼的了?和substr/string有什麼區別? }; console.log(accum("CHina")); 複製程式碼
寫完並且測試結果正確, 就開始沾沾自喜, 感覺萬事大吉。( 這種狀態很像在工作中, 寫完功能不去優化一樣 )
上面的一坨程式碼, 對, 就是一坨程式碼, 一坨像極了業務功能的邏輯程式碼, 沒有精巧的思路, 沒有精緻的寫法。 這踏馬跟鹹魚有什麼區別?
優雅的迴圈
const accum = str => { let result = ""; for (let i = 0; i < str.length; i++) { const temp = str[i]; result += temp.toUpperCase(); for (let j = i; j > 0; j--) { result += temp.toLowerCase(); } result += "-"; } return result.slice(0, -1); }; console.log(accum("CHina")); 複製程式碼
優雅的迴圈, 優雅的迴圈, 優雅的迴圈 啊、啊、啊!
精緻的利己主義者
const accum = str => { return Array.from(str.toLowerCase(), (item, index) => { return ( item.toUpperCase() + Array.from({length: index}, () => { return item; } ).join("") ); }).join("-"); }; console.log(accum("CHina")); 複製程式碼
放蕩不羈的 reduce
const accum = str => { return Array.from(str.toLowerCase()).reduce((accu, cur, idx) => { accu.push(cur.toUpperCase().padEnd(idx + 1, cur)); return accu; }, []).join("-"); }; console.log(accum("CHina")); 複製程式碼
百辟匕首( RegExp )
匹配與獲取字串方法
const accum = str => { return str.toLowerCase().replace(/\w{1}/gi, (item, idx) => { let temp = ""; Array.from(new Array(idx)).map(() => { temp += item; }); return `${item.toUpperCase()}${temp}-`; }).slice(0, -1); }; console.log(accum("CHina")); 複製程式碼
怎麼樣, 最後幾種方案看的是不是很刺激、很驚喜, 其實就是一堆奇葩操作, 這是API
操作者的狂歡, 也是JS
開發者的基本功^_^
這幾個方案裡面最令人驚喜的還是replace
, 當第二個引數是一個函式, 當第一個引數為正則表示式並且為全域性匹配模式時, 這個方法每次匹配都會被呼叫。
replace 應該是正則的 6 個常用 API 中最強大的一個, 它可以拿到你想要的資訊, 並且假借替換之名, 做一些神奇操作
傳送門 ->正則操作的6個常用方法( 字串例項4個, 正則例項2個 )
注:
- \w 匹配單詞字元, 等價於[0-9a-ZA-Z_], 數字字母下劃線
- {1} 連續出現 1 次