第五章 基本引用类型
这是我参与8月更文挑战的第19天,活动详情查看: 8月更文挑战
5.2 RegExp
ECMAScript 通过 RegExp 类型支持正则表达式。正则表达式使用类似 Perl 的简洁语法来创建:
let expression = /pattern/flags;
这个正则表达式的 pattern(模式)可以是任何简单或复杂的正则表达式,包括字符类、限定符、 分组、向前查找和反向引用。每个正则表达式可以带零个或多个 flags(标记),用于控制正则表达式 的行为。下面给出了表示匹配模式的标记。
- g:全局模式,表示查找字符串的全部内容,而不是找到第一个匹配的内容就结束。
- i:不区分大小写,表示在查找匹配时忽略 pattern 和字符串的大小写。
- m:多行模式,表示查找到一行文本末尾时会继续查找。
- y:粘附模式,表示只查找从 lastIndex 开始及之后的字符串。
- u:Unicode 模式,启用 Unicode 匹配。
- s:dotAll 模式,表示元字符.匹配任何字符(包括\n 或\r)。
使用不同模式和标记可以创建出各种正则表达式,比如:
// 匹配字符串中的所有"at"
let pattern1 = /at/g;
// 匹配第一个"bat"或"cat",忽略大小写
let pattern2 = /[bc]at/i;
// 匹配所有以"at"结尾的三字符组合,忽略大小写
let pattern3 = /.at/gi;
与其他语言中的正则表达式类似,所有元字符在模式中也必须转义,包括:
( [ { \ ^ $ | ) ] } ? * + .
元字符在正则表达式中都有一种或多种特殊功能,所以要匹配上面这些字符本身,就必须使用反斜 杠来转义。下面是几个例子:
// 匹配第一个"bat"或"cat",忽略大小写
let pattern1 = /[bc]at/i;
// 匹配第一个"[bc]at",忽略大小写
let pattern2 = /[bc]at/i;
// 匹配所有以"at"结尾的三字符组合,忽略大小写
let pattern3 = /.at/gi;
// 匹配所有".at",忽略大小写
let pattern4 = /.at/gi;
这里的 pattern1 匹配"bat"或"cat",不区分大小写。要直接匹配"[bc]at",左右中括号都必 须像 pattern2 中那样使用反斜杠转义。在 pattern3 中,点号表示"at"前面的任意字符都可以匹配。 如果想匹配".at",那么要像 pattern4 中那样对点号进行转义。
前面例子中的正则表达式都是使用字面量形式定义的。正则表达式也可以使用 RegExp 构造函数来 创建,它接收两个参数:模式字符串和(可选的)标记字符串。任何使用字面量定义的正则表达式也可 以通过构造函数来创建,比如:
// 匹配第一个"bat"或"cat",忽略大小写
let pattern1 = /[bc]at/i;
// 跟 pattern1 一样,只不过是用构造函数创建的
let pattern2 = new RegExp("[bc]at", "i");
这里的 pattern1 和 pattern2 是等效的正则表达式。注意,RegExp 构造函数的两个参数都是字符串。因为 RegExp 的模式参数是字符串,所以在某些情况下需要二次转义。所有元字符都必须二次转义,包括转义字符序列,如**\n**(\转义后的字符串是\,在正则表达式字符串中则要写成\)。下表展示了几个正则表达式的字面量形式,以及使用 RegExp 构造函数创建时对应的模式字符串。
字面量模式 | 对应的字符串 |
---|---|
/[bc]at/ | "[bc]at" |
/.at/ | ".at" |
/name/age/ | "name/age" |
/\d.\d{1,2}/ | "\d.\d{1,2}" |
/\w\hello\123/ | "\w\hello\123" |
此外,使用 RegExp 也可以基于已有的正则表达式实例,并可选择性地修改它们的标记:
const re1 = /cat/g;
console.log(re1); // "/cat/g"
const re2 = new RegExp(re1);
console.log(re2); // "/cat/g"
const re3 = new RegExp(re1, "i");
console.log(re3); // "/cat/i"
5.2.1 RegExp 实例属性
每个 RegExp 实例都有下列属性,提供有关模式的各方面信息。
- global:布尔值,表示是否设置了 g 标记。
- ignoreCase:布尔值,表示是否设置了 i 标记。
- unicode:布尔值,表示是否设置了 u 标记。
- sticky:布尔值,表示是否设置了 y 标记。
- lastIndex:整数,表示在源字符串中下一次搜索的开始位置,始终从 0 开始。
- multiline:布尔值,表示是否设置了 m 标记。
- dotAll:布尔值,表示是否设置了 s 标记。
- source:正则表达式的字面量字符串(不是传给构造函数的模式字符串),没有开头和结尾的 斜杠。
- flags:正则表达式的标记字符串。始终以字面量而非传入构造函数的字符串模式形式返回(没 有前后斜杠)。
通过这些属性可以全面了解正则表达式的信息,不过实际开发中用得并不多,因为模式声明中包含 这些信息。下面是一个例子:
let pattern1 = /[bc]at/i;
console.log(pattern1.global); // false
console.log(pattern1.ignoreCase); // true
console.log(pattern1.multiline); // false
console.log(pattern1.lastIndex); // 0
console.log(pattern1.source); // "[bc]at"
console.log(pattern1.flags); // "i"
let pattern2 = new RegExp("\[bc\]at", "i");
console.log(pattern2.global); // false
console.log(pattern2.ignoreCase); // true
console.log(pattern2.multiline); // false
console.log(pattern2.lastIndex); // 0
console.log(pattern2.source); // "[bc]at"
console.log(pattern2.flags); // "i"
注意,虽然第一个模式是通过字面量创建的,第二个模式是通过 RegExp 构造函数创建的,但两个 模式的 source 和 flags 属性是相同的。source 和 flags 属性返回的是规范化之后可以在字面量中 使用的形式。
\