参考文档:https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Guide/Regular_Expressions
1、将用户输入转换成正则表达式中字面字符串
function escapeRegExp(string) {
return string.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
//$&表示整个被匹配的字符串
}
2、正则表达式标志
g
全局搜索。 i
不区分大小写搜索。 m
多行搜索。 s
允许 .
匹配换行符。 u
使用unicode码的模式进行匹配。 y
执行“粘性(sticky
)”搜索,匹配从目标字符串的当前位置开始
3、正则常用方法
test 方法执行一个检索,用来查看正则表达式与指定的字符串是否匹配。返回 true
或 false
。 /*
语法
regexObj.test(str)
如果正则表达式设置了全局标志,test() 的执行会改变正则表达式
lastIndex属性。连续的执行test()方法,后续的执行将会从
lastIndex 处开始匹配字符串。
*/
var re = /^./g;
console.log(re.test("foo"));//true
console.log(re.lastIndex);//1
console.log(re.test("foo"));//false
//不加全局标志
var re = /^./;
console.log(re.test("foo"));//true
console.log(re.lastIndex);//0
console.log(re.test("foo"));//true
//也可以手动修改lastindex
var re = /^./g;
re.lastIndex=1;
console.log(re.test("foo"));//false
exec 在一个指定字符串中执行一个搜索匹配。返回一个结果数组或null。 /*
语法
regexObj.exec(str)
在有全局标志的情况下会把上次成功匹配后的位置记录在
lastIndex 属性中,且可以根据lastIndex进行遍历匹配结果
如果匹配失败,exec() 方法返回 null,并将 lastIndex 重置为 0
*/
var re = /quick\s(?<name1>brown).+?(?<name2>jumps)/ig;
var result = re.exec('The Quick Brown Fox Jumps Over The Lazy Dog');
console.log(result);
/*
output:
0: "Quick Brown Fox Jumps" //全部匹配会存在数组下标0位置
捕获组会从数组下标1依次往后进行存储,我们可以通过下标
对每一个捕获组进行遍历
1: "Brown"
2: "Jumps"
捕获组命名,通过(?<>)方式来命名
groups: {name1: "Brown", name2: "Jumps"}
index: 4 //对字符串开始匹配的歧视位置,即例中的Q位置
input: "The Quick Brown Fox Jumps Over The Lazy Dog"//原始字符串
console.log(RegExp.prototype);
原型链中的常用属性
lastIndex: 下一次匹配开始的位置
ignoreCase :是否使用了 "i" 标记使正则匹配忽略大小写
global :是否使用了 "g" 标记来进行全局的匹配
multiline :是否使用了 "m" 标记使正则工作在多行模式
source : 正则匹配的字符串
flags :正则标志
*/
match 检索返回一个字符串匹配正则表达式的结果 /*
语法
str.match(regexp)
一个正则表达式对象。如果传入一个非正则表达式对象,则会隐式
地使用 new RegExp(obj) 将其转换为一个 RegExp 。如果你没有
给出任何参数并直接使用match() 方法 ,
你将会得到一个包含空字符串的 Array :[""] 。
*/
//如果使用g标志,则将返回与完整正则表达式匹配的所有结果,
但不会返回捕获组
var str = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
var regexp = /[A-E]/gi;
var matches_array = str.match(regexp);
console.log(matches_array);
// ['A', 'B', 'C', 'D', 'E', 'a', 'b', 'c', 'd', 'e']
//如果未使用g标志,则仅返回第一个完整匹配及其相关的捕获组(Array)。
在这种情况下,返回的项目将具有如下所述的其他属性。同exec方法
var str = 'For more information, see Chapter 3.4.5.1';
var re = /see (chapter \d+(\.\d)*)/i;
var found = str.match(re);
console.log(found);
// logs [ 'see Chapter 3.4.5.1',
// 'Chapter 3.4.5.1',
// '.1',
// index: 22,
// input: 'For more information, see Chapter 3.4.5.1' ]
// 'see Chapter 3.4.5.1' 是整个匹配。
// 'Chapter 3.4.5.1' 被'(chapter \d+(\.\d)*)'捕获。
// '.1' 是被'(\.\d)'捕获的最后一个值。
// 'index' 属性(22) 是整个匹配从零开始的索引。
// 'input' 属性是被解析的原始字符串。
matchAll 返回一个包含所有匹配正则表达式的结果及分组捕获组的迭代器 /*
语法
str.matchAll(regexp)
返回一个包含所有匹配正则表达式的结果及分组捕获组的迭代器,matchAll必须加全局g标志,
不加会抛异常
matchAll匹配时lastIndex值并不会改变
*/
const regexp = RegExp('foo[a-z]*','g');
const str = 'table football, foosball';
const matches = str.matchAll(regexp);
for (const match of matches) {
console.log(`Found ${match[0]} start=${match.index}
end=${match.index + match[0].length}.`);
}
// expected output: "Found football start=6 end=14."
// expected output: "Found foosball start=16 end=24."
// matches iterator is exhausted after the for..of iteration
// Call matchAll again to create a new iterator
Array.from(str.matchAll(regexp), m => m[0]);
// Array [ "football", "foosball" ]
//matchAll可以更方便的获取捕获组
let array = [...str.matchAll(regexp)];
array[0];
// ['test1', 'e', 'st1', '1', index: 0, input: 'test1test2', length: 4]
array[1];
// ['test2', 'e', 'st2', '2', index: 5, input: 'test1test2', length: 4]
search 执行正则表达式和 String
对象之间的一个搜索匹配 /*
语法
str.search(regexp)
如果匹配成功,则 search() 返回正则表达式在字符串中首次匹配项的索引;
否则,返回 -1
*/
var str = "hey JudE";
var re = /[A-Z]/g;
var re2 = /[.]/g;
console.log(str.search(re));
// returns 4, which is the index of the first capital letter "J"
console.log(str.search(re2));
// returns -1 cannot find '.' dot punctuation
replace 返回一个由替换值(replacement
)替换部分或所有的模式(pattern
)匹配项后的新字符串。模式可以是一个字符串或者一个正则表达式,替换值可以是一个字符串或者一个每次匹配都要调用的回调函数。如果pattern
是字符串,则仅替换第一个匹配项。 /*
语法
str.replace(regexp|substr, newSubStr|function)
方法并不改变调用它的字符串本身,而只是返回一个新的替换后的字符串。
替换字符串可以插入下面的特殊变量名
$$ 插入一个 "$"。
$& 插入匹配的子串。
$` 插入当前匹配的子串左边的内容。
$' 插入当前匹配的子串右边的内容。
$n 插入第 n 个括号匹配的字符串。提示:索引是从1开始
match 匹配的子串。(对应于上述的$&。)
p1,p2, ... 对应于上述的$1,$2等
offset 匹配到的子字符串在原字符串中的偏移量。
(比如,如果原字符串是 'abcd',匹配到的子字符串是 'bc',那么这个参数将会是 1)
string 被匹配的原字符串。
*/
function replacer(match, p1, p2, p3, offset, string) {
// p1 is nondigits, p2 digits, and p3 non-alphanumerics
return [p1, p2, p3].join(' - ');
}
var newString = 'abc12345#$*%'.replace(/([^\d]*)(\d*)([^\w]*)/, replacer);
console.log(newString); // abc - 12345 - #$*%
split 指定的分隔符字符串将一个String对象分割成子字符串数组,以一个指定的分割字串来决定每个拆分的位置。 /*
语法
str.split([separator[, limit]])
separator
指定表示每个拆分应发生的点的字符串。separator
可以是一个字符串或正则表达式。 如果纯文本分隔符包含多个字符,
则必须找到整个字符串来表示分割点。如果在str中省略或不出现分隔符,
则返回的数组包含一个由整个字符串组成的元素。如果分隔符为空字符串,
则将str原字符串中每个字符的数组形式返回。
limit
一个整数,限定返回的分割片段数量。当提供此参数时,split 方法
会在指定分隔符的每次出现时分割该字符串,但在限制条目已放入数组时停止
。如果在达到指定限制之前达到字符串的末尾,它可能仍然包含少于限制的条目。
新数组中不返回剩下的文本。
*/
//使用一个数组来作为分隔符
const myString = 'this|is|a|Test';
const splits = myString.split(['|']);
console.log(splits); //["this", "is", "a", "Test"]
const myString = 'ca,bc,a,bca,bca,bc';
const splits = myString.split(['a','b']);
// myString.split(['a','b']) is same as myString.split(String(['a','b']))
console.log(splits); //["c", "c,", "c", "c", "c"]
靠正则来分割使结果中包含分隔块,如果 separator 包含捕获括号
(capturing parentheses),则其匹配结果将会包含在返回的数组中。
var myString = "Hello 1 word. Sentence number 2.";
var splits = myString.split(/(\d)/);
console.log(splits);
//output:[ "Hello ", "1", " word. Sentence number ", "2", "." ]
限制返回值中分割元素数量
var myString = "Hello World. How are you doing?";
var splits = myString.split(" ", 3);
console.log(splits);
//output:["Hello", "World.", "How"]