JS正则表达式-速记通关小抄

135 阅读3分钟

JS 正则表达式-速记通关小抄

[TOC]

基本元字符

元字符含义
.匹配除 换行符 以外的任何字符
|逻辑或操作符
[]定义一个集合,匹配集合中的一个字符,在这个集合里,所有的元字符都会失效,都会变为一个普通字符
[^]对上面的集合取非
-代表一个区间,例如[a-z]
\表示下一个字符是特殊的,不能从字面上解释。比如 n 就代表n,如果在前面加上\,那么\n就代表了换行符。同理/a*/ 代表匹配a字符,如果在 * 前面加上\,就代表匹配 a*

数量元字符

元字符含义
{m,n}匹配前面一个字符至少m次 至多n次重复。
+记忆方式追加(+),起码得有一次
*记忆方式乘法(*),可以一次都没有
单独使用匹配前面一个表达式零次或者一次,相当于 {0,1},记忆方式,有吗?,有(1)或者没有(1),如果跟在任何量词*,+,?,{}后面的时候将会使量词变为非贪婪模式(尽量匹配少的字符),默认是使用贪婪模式。比如对 "123abc" 应用 /\d+/ 将会返回 "123",如果使用 /\d+?/,那么就只会匹配到 "1"

:notebook: 再次解释

?元字符 的使用分为2种,一种是在普通字符后面A,一种是在数量元字符后面B。A情况很好理解,要么匹配0次,要么匹配1次;B情况是改变前一位量词的贪婪模式,将前一位量词转换为非贪婪模式,比如:

let x1 = 'https://12.10.30/xx-ctr.sty';
let regexp1 = /[1-9]+/;
let regexp2 = /[1-9]+?/;
x1.match(regexp1);         // ['12']
x1.match(regexp2);         // ['1']

位置元字符

元字符含义
^匹配以表达式 为开头的字符
\$匹配以表达式 为结尾的字符
(?=p)匹配p前面的位置
(?!p)匹配不是p前面的位置

标志元字符

元字符含义
g全局搜索
i忽略大小写
m多行匹配

分支结构

正则是是通过 | 符号来表达 的意思。具体如下:

let regexp1 = /p1|p2/;
// 匹配出来的结果,要么符合p1,要么符合p2, 绝对不会是pp2

请看下面的测试:

let str = 'https://12.10.30.110.26/xx-ctr.sty';
let regexp1 = /[1-9]+/;
let regexp2 = /[1-9]+?/g;
let regexp3 = /12|10/g;
let regexp4 = /12 | 10/g;
let regexp5 = /12 |10/g;
let regexp6 = /[1-9]+?/;
console.log('匹配出来的结果-1:', x1.match(regexp1));   // 12
console.log('匹配出来的结果-2:', x1.match(regexp2));   // 1、2、1、3、1、1、2、6
console.log('匹配出来的结果-3:', x1.match(regexp3));   // 12、10
console.log('匹配出来的结果-4:', x1.match(regexp4));   // null
console.log('匹配出来的结果-5:', x1.match(regexp5));   // 10
console.log('匹配出来的结果-6:', x1.match(regexp6));   // 1

引用分组

在正则表达式里,使用括号代表分组,以 左括号的出现顺序 代表 这是第几个分组。

那分组有啥用呢?它可以帮我们提取子数据。

let x1 = 'https://12.10.30.110.26/xx-ctr.sty';
let regexp7 = /([1-9]+\.)/;

x1.match(regexp7);

// 返回的结果的数据格式如下:
[
    '12.',     // 正则返回的结果
    '12.',     // 正则里第一个分组的结果
    ...,       // 如果有第二个分组,那么就接着往后排
    index: 8,  // 正则返回的结果在字符串中的位置
    input: 'https://12.10.30.110.26/xx-ctr.sty',
    groups: undefined
]

接下来,我们栽看一下多括号的情况:

let x1 = 'https://12.10.30.110.26/xx-ctr.sty';
let regexp9 = /((https:)(\/\/))/;  //第几个分组 对应 第几个左侧开括号 

x1.match(regexp9);

// 返回的数据格式如下:
[
    'https://',        // 正则匹配的结果
    'https://',        // 第一个分组的结果    ((https:)(\/\/))
    'https:',          // 第二个分组的结果    (https:)
    '//',              // 第三个分组的结果    (\/\/)
    index: 0,
    input: 'https://12.10.30.110.26/xx-ctr.sty',
    groups: undefined
]

有的时候,我们想在正则表达式里引用前面第一个分组对应的结果,或者是前面第二个分组对应的结果。

我们可以使用 \1来获取前面第一个分组对应的结果,\N 就是代表获取前面第N个分组对应的结果。

let regexp10 = /\d{4}(-|\/|\.)\d{2}\1\d{2}/;
let x1 = "2023-03/04";

regexp10.test(x1); // false