29.22分鐘學會書寫正則(2)

寫在前面的一些廢話

沒有看過上一篇文章的盆友有福了!

今天!沒錯!就是現在!我將免費!all f*cking FREE!

免費將上篇文章的鏈接發出來!

這裏是上篇

上回說了怎麼寫出正則,這次展示下在js中使用正則的場景

正則對象屬性

javascript的正則對象有以下幾個屬性,其中前面三個也叫修飾符(也就是/表達式/兩條槓後面的字符,比如上一篇文章出現的 /\bis\b/g 的這個g)。

  • global:是否全文搜索,默認false
  • ignoreCase:是否大小寫敏感,默認false,即不忽略大小寫
  • multiline:是否多行搜索,默認false
  • lastIndex:當前表達式匹配內容的最後一個字符的下一個位置
  • source:正則表達式的文本字符串,也就是“/表達式/修飾符”中的表達式,var reg=/\bis\b/g; reg.source就是\bis\b

正則相關的方法

js中,RegExp對象有兩個內置方法

  • test
  • exec

此外,還有一些String對象的方法也支持正則表達式,它們是

  • search
  • match
  • split
  • replace

test()

test() 方法用於檢測一個字符串是否匹配某個模式,返回true或者false.

var reg = /\w/;
reg.test('abc');
//true
reg.test('abc');
//true
reg.test('abc');
//true
reg.test('@#$%')
//false
reg.test('@#$%')
//false
//爲什麼要多執行幾遍呢?你可能會以爲樓主lu多了導致老眼昏花多輸入了幾遍。but NO!多執行幾遍是爲了和下面作對比。

當我們的正則表達式加上了g修飾符以後,這個方法出現了一些不同

var reg = /\w/g;
reg.test('abc');//true
reg.test('abc');//true
reg.test('abc');//true
reg.test('abc');//false

clipboard.png
爲什麼會這樣呢?因爲當我們加上全局搜索這個修飾符後,test()方法會返回結果,並且更新reg對象的屬性(lastIndex),他會在上一次lastIndex的位置開始往後查找,而不是從頭開始。
所以這個方法建議不要加g,如果你這個人比較倔強,非要加的話,你可以每次都重新初始化一個正則對象,因爲它第一次的結果是和沒有加g的時候是一樣的。
Like this。

var reg = /\w/g;reg.test('abc');//true
//每次都初始化正則對象,把這兩行寫在一行裏比較好複製,因爲分開復制一不小心就出現了上面的問題

exec()

exec()方法用於使用正則表達式對字符串執行搜索,並將更新全局RegExp對象的屬性以反應匹配結果
如果沒有匹配到文本則返回null,否則返回一個結果數組:

  • 數組第一個元素是與正則表達式相匹配的文本
  • 第二個元素是與正則表達式的第一個子表達式(也就是分組1)相匹配的文本(如果有分組1的話)
  • 第三個元素是與正則表達式的第二個子表達式(分組2)相匹配的文本(如果有分組2的話)
  • 除了數組元素和 length 屬性之外,exec() 方法還返回兩個屬性。index 屬性聲明的是匹配文本的第一個字符的位置。input 屬性則存放的是被檢索的字符串 string。
var reg = /(\d)(\w)/  //上篇文章已經介紹過分組了,這裏的兩個括號分別是分組1和分組2
reg.exec('1a2b3c4d5e');

clipboard.png

當我們的正則表達式加上了g修飾符以後,這個方法又出現了一些不同

var reg = /(\d)(\w)/g
reg.exec('1a2b3c4d5e');

還是上圖片比較簡單~
clipboard.png
這個表現跟test是一個尿性的,即非全局調用(不加g)的時候不會更新lastIndex(lastIndex不生效),全局調用的時候會更新lastIndex

說完了比較複雜的有分組的情況,我們來看看沒有分組的情況,言簡意賅,你作爲這麼優秀的一個人,應該能隨便看懂吧。

var reg = /\d\w/  
reg.exec('1a2b3c4d5e');

clipboard.png

對於這個方法呢,如果我們只需要查找第一個匹配結果的話可以不加g,如果需要返回所有匹配結果的話,需要循環執行reg.exec(),並且需要加上g。

search()

search()方法用於檢索字符串中制定的子字符串或者檢索與正則表達式相匹配的子字符串。

方法返回第一個匹配結果的index,查找不到返回-1
search()方法會忽略g標誌,總是從字符串的開頭進行檢索

當我們傳入的參數s字符串時,它會轉換成正則表達式
var str = "abcd1234"
str.search('1') //4
str.search(/1/) //4
str.search('hello') //-1
str.search(/hello/) //-1

so easy~下一個

match()

非全局調用情況下(不加g):
這個方法類似於exec(),返回值是一毛一樣的,one hair one style。
match()方法可在字符串內檢索指定的值,或找到一個或多個正則表達式的匹配
如果沒有匹配到文本則返回null,否則返回一個結果數組:

  • 數組第一個元素是與正則表達式相匹配的文本
  • 第二個元素是與正則表達式的第一個子表達式(也就是分組1)相匹配的文本(如果有分組1的話)
  • 第三個元素是與正則表達式的第二個子表達式(分組2)相匹配的文本(如果有分組2的話)
  • 除了數組元素和 length 屬性之外,match() 方法還返回兩個屬性。index 屬性聲明的是匹配文本的第一個字符的位置。input 屬性則存放的是被檢索的字符串 string。
var str = "1a2b3c4d";
var reg = /(\d)(\w)/;
str.match(reg);

clipboard.png

當我們的正則表達式加上了g修飾符以後,這個方法又出現了一些不同,我爲什麼要說‘又’

match()方法的返回改變了,變化害...害挺大的,跟前面的exec()和test()方法又有不同

如果沒有匹配到文本則返回null,否則返回一個結果數組:

  • 數組元素爲與正則表達式匹配的文本
var str = "1a2b3c4d";
var reg = /(\d)(\w)/g;
str.match(reg);

clipboard.png

你有沒有發現,即使我已經貼了圖,卻還是寫了代碼,爲什麼?
因爲作爲一個這麼sweet 和 warm的人,我有必要爲你節省你自己輸入代碼的時間,你現在只需要ctrl C 然後ctrl V就可以在瀏覽器控制瘋狂驗證我的圖片,瘋狂測試這些方法!

split()

split()方法用於把一個字符串分割成字符串數組。

//這個也可以輸入字符串作爲參數,類似於search(),它會轉換成正則
var str = "a,b,c,d"
str.split(','); //["a","b","c","d"]
str.split(/,/); //["a","b","c","d"]
//一般情況都是使用字符串居多,比較複雜的情況就可以使用正則
var str ="a1b2c3";
str.split(/\d/); //["a", "b", "c", ""]
//注意:如果字符串最後的子字符串剛好符合參數的正則,那麼就會多了一個空的元素,像上面一樣

replace()

來了來了,上篇文章中使用最多的replace()終於來了!!!AV8D shout with me! RRRRRRRRrrrrrrrrrrrrrr~EEEEEEE~PPPPP~LLLL~AAAA~CCCCC~EEEEE。

該方法用於在字符串中用一些字符替換另一些字符,或替換一個與正則表達式匹配的子串。

1、 一般用法,這裏是一般用法啊,replace('找誰','替換成誰')

該用法的全局與非全局調用的差別是‘替換第一個匹配項’和‘替換所有匹配項’。

舉個常用的例子

//這個‘找誰’同樣也可以是字符串或者是正則,類似於split(),search()
var str = "hello I am leelei";
str.replace('leelei','嶺南吳彥祖'); //"hello I am 嶺南吳彥祖"
str.replace(/leelei/,'嶺南吳彥祖'); //"hello I am 嶺南吳彥祖"

好吧,這個對於你們來說並不常用,可能是隻有我在用而已,抱歉。寫個你們常用的例子吧

var str = "2018-11-26";
str.replace(/-/,'/');  //"2018/11-26"
//看到沒有,這裏只替換了一個-
str.replace(/-/g,'/');  //"2018/11/26"
//只有全局調用的時候,纔會替換所有的匹配文本

2、 進階用法,replace('找誰',回調函數),每次匹配替換的時候調用,有4個參數

  • 1、匹配的字符串
  • 2、正則表達式分組內容,沒有分組就沒有這個這個參數,幾個分組就幾個該參數
  • 3、匹配項在字符串中的index
  • 4、原字符串,replace()方法不會改變原字符串的哦。
//**當沒有分組的時候**
var str ="a5b6c7d8";
//可以根據下面的截圖對照上面的參數來理解記憶。
//這裏是給每一個匹配的數字+1.
str.replace(/\d/g,function(match,index,origin){
    console.log(match,index,origin);
    return match-0+1;
});

clipboard.png

//**當有分組的時候**
//爲字符串中的某些字段更換樣式,完整的demo就不寫了,大家應該都能看懂吧。
//將第一個分組匹配的內容替換掉
//爲什麼要分組? 因爲我們不想給'個'這個字添加樣式,但是又需要用'個'來判斷,我們只更改'個'前面的數字的樣式,不更改其他數字。
var str = "第1點,這裏有4個橘子,5個橙子,9個蘋果,我們需要爲這幾個數量更改樣式.";
str.replace(/(\d)個/g,function(match,$1,index,origin){
    console.log(match,$1);
    return "<span style='color:red'>"+$1+"<span>個";
})
//需要注意的是,這個回調函數的return值會覆蓋match的值,因此要在return的時候加回'個'字。

clipboard.png
ok~應該足夠清楚了吧~

最後

雖然標題是29.22分鐘,但是看完兩篇文章好像就不止了。
我不管,30分鐘內沒看完的好好檢討下自己,是不是沒有戴眼鏡,是不是沒睡好覺,看那麼慢呢!

如果有建議或者意見,請在評論區指出,非常感謝~

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章