1. Js 中关于正则的 API
1.1 String 中的方法
-
search
search() 方法用于检索字符串中指定的子字符串,或检索与正则表达式相匹配的子字符串。 如果没有找到任何匹配的子串,则返回 -1。
var str="Mr. Blue has a blue house"; console.log(str.search(/blue/i)); // => 4 // 注意 /i 表示对大小写忽略,所以找到了 Blue 的位置,即为 4
-
split
split() 方法用于把一个字符串分割成字符串数组,接受的参数为字符串或正则表达式。
var str="How are you doing today?"; var n=str.split(/\s/); console.log(n); // => ["How", "are", "you", "doing", "today?"]
-
match
match() 方法可在字符串内检索指定的值,或找到一个或多个正则表达式的匹配,接受的参数为
regexp
。注意:match 返回结果的格式,与正则对象是否有修饰符
g
有关。-
没有
g
,返回的是标准匹配格式,即数组的第一个元素是整体匹配的内容,接下来是分组捕获的内容,然后是整体匹配的第一个下标,最后是输入的目标字符串。 -
有
g
,返回的是所有匹配的内容。 -
当没有匹配时,不管有无 g,都返回 null。
var string = "2019/06/18"; var regex1 = /\b(\d+)\b/; var regex2 = /\b(\d+)\b/g; console.log( string.match(regex1) ); console.log( string.match(regex2) ); // => ["2019", "2019", index: 0, input: "2019/06/18", groups: undefined] // => ["2019", "06", "18"]
-
-
replace
replace() 方法用于在字符串中用一些字符替换另一些字符,或替换一个与正则表达式匹配的子串。语法为
string.replace(regexp|substr, newSubStr|function)
。replace 有两种使用形式,因为它的第二个参数,可以是字符串,也可以是函数。
- 当第二个参数是字符串时,我们可以用
$1,$2,...,$99
来匹配第1-99
个分组里捕获的文本
var result = "2,3,5".replace(/(\d+),(\d+),(\d+)/, "$3=$1+$2"); console.log(result); // => "5=2+3"
-
当第二个参数是函数时,在这种情况下,当匹配执行后,该函数就会执行。函数的返回值作为替换字符串。 注意:如果第一个参数是正则表达式,并且其为全局匹配模式,那么这个方法将被多次调用,每次匹配都会被调用。下面是该函数的参数。
参数 含义 match
匹配的子串 $1, $2, ...
匹配的分组,对应于上例的 $1,$2,...
index
匹配到的子字符串在原字符串中的下标 input
被匹配的原字符串 如下例,匹配一个四位数字,把中间两位数字变成
**
var result = "1234 2345 3456".replace(/(\d)\d{2}(\d)/g, function (match, $1, $2, index, input) { console.log([match, $1, $2, index, input]); return `${$1}**${$2}` }); console.log(result); // => ["1234", "1", "4", 0, "1234 2345 3456"] // => ["2345", "2", "5", 5, "1234 2345 3456"] // => ["3456", "3", "6", 10, "1234 2345 3456"] // => 1**4 2**5 3**6
- 当第二个参数是字符串时,我们可以用
1.2 RegExp 中对象方法
-
exec
exec() 方法用于检索字符串中的正则表达式的匹配。如果字符串中有匹配的值返回该匹配值,否则返回 null。
var str="Hello world!"; var patt=/Hello/g; var result=patt.exec(str); console.log(result); // => ["Hello", index: 0, input: "Hello world!", groups: undefined]
-
test
test() 方法用于检测一个字符串是否匹配某个模式。如果字符串中有匹配的值返回 true ,否则返回 false。
var str="Hello world!"; var patt=/Hello/g; var result=patt.test(str); console.log(result); // => true
2. 常用正则表达式
2.1 数字的千位符表示
情形:把一串整数转换成千位分隔形式,例如 12345678
,转换成 12,345,678
。
思路:从个位往左数起,每三位前插入一个千位分隔符,即可以想象成我们要把每三位数字前面的空 ""
(即位置)匹配出来,并替换成千位分隔符。
做法:首先因为需要从右往左匹配,$
是必须要有的。三位数字用 \d{3}
,不确定多少组,用 (\d{3})+
,所以目前为 /(\d{3})+$/g
。
由于替换的是位置,所以需要用到位置锚 (?=p)
,即 /(?=(\d{3})+$)/g
:
var result = "12345678".replace(/(?=(\d{3})+$)/g, ',')
console.log(result);
// => 12,345,678
但如果是 9
位数字的话,
var result = "123456789".replace(/(?=(\d{3})+$)/g, ',')
console.log(result);
// => ,123,456,789
所以我们可以在匹配的位置前加一个非单词边界 \B
,
即 /(?=(\B\d{3})+$)/g
:
var result = "123456789".replace(/(?=(\B\d{3})+$)/g, ',')
console.log(result);
// => 123,456,789
2.2 模拟 trim 方法
情形:去掉字符串的开头和结尾的空白符
思路:还是匹配位置,替换成 ''
做法:
function trim(str) {
return str.replace(/^\s+|\s+$/g, '');
}
console.log(trim(" test ") );
// => test
2.3 单词首字母大写
情形:把 i'm a curious babe
转化成 I'm A Curious Babe
思路: 找到首字母并替换之
做法:
function upperTitle(str) {
return str.replace(/(^|\s)\w/g, function(match) {
return match.toUpperCase();
})
}
console.log(upperTitle("i'm a curious babe"));
// => I'm A Curious Babe
驼峰化的思路是一样的:
function camelize (str) {
return str.replace(/[-_\s]+(.)?/g, function (match, c) {
console.log(match, c);
return c ? c.toUpperCase() : '';
});
}
console.log(camelize('-moz-transform'));
// => -m m
// => -t t
// => MozTransform
2.4 验证身份证
情形: 15 或者 18 位身份证号,尾数可以是数字及 X 或者 x
做法:(^\d{15}$)|(^\d{17}(\d|X|x)$)
var reg = /(^\d{15}$)|(^\d{17}(\d|X|x)$)/;
var id = '25271618827172817X';
console.log(reg.test(id));
// => true
2.5 验证手机号
情形:以 1 开头,第二位数是 3/4/5/7/8 的 11 位手机号码
做法:^1[3,4,5,7,8,9]\d{9}$
2.6 验证邮箱
情形:以大写字母 [A-Z]
、小写字母 [a-z]
、数字[0-9]
、下滑线_
、减号-
及点号.
开头,并需要重复一次至多次[+]
;
中间必须包括 @
符号;
@
之后需要连接大写字母 [A-Z]
、小写字母 [a-z]
、数字 [0-9]
、下滑线 _
、减号 -
及点号.
,并需要重复一次至多次[+]
;
结尾必须是点号 .
连接2至4位的大小写字母 [A-Za-z]{2,4}
。
做法:/^([A-Za-z0-9_\-\.])+\@([A-Za-z0-9_\-\.])+\.([A-Za-z]{2,4})$/
var reg = /^([A-Za-z0-9_\-\.])+\@([A-Za-z0-9_\-\.])+\.([A-Za-z]{2,4})$/;
var email = 'test-babe@163.com';
console.log(reg.test(email));
2.7 验证密码
情形:密码长度 6-12 位,由数字、小写字母和大写字母组成,但必须至少包括 2 种字符。
思路1:密码长度6-12位,由 [\da-zA-Z]
组成,可以写成 /^[\dA-Za-z]{6,12}$/
;
至少包含数字,可以写成 /(?=.*\d)/
那么,至少包含两种字符就变成了 - 同时包含数字和小写字母 - 同时包含数字和大写字母 - 同时包含小写字母和大写字母 - 同时包含数字、小写字母和大写字母(这种情况被前三种情况包含)
做法1:所以最终写法为:/((?=.*\d)(?=.*[a-z])|(?=.*\d)(?=.*[A-Z])|(?=.*[a-z])(?=.*[A-Z]))^[\dA-Za-z]{6,12}$/
var regex = /((?=.*\d)(?=.*[a-z])|(?=.*\d)(?=.*[A-Z])|(?=.*[a-z])(?=.*[A-Z]))^[\dA-Za-z]{6,12}$/;
console.log(regex.test("1234567"));
console.log(regex.test("1234567AZ"));
console.log(regex.test("1234567AZx"));
// false
// true
// true
思路2:至少包含两种字符的意思就是说,不能全部都是数字,也不能全部都是小写字母,也不能全部都是大写
字母。
不能全部是数字的正则是:(?!^\d{6, 12}$)^[\da-zA-Z]{6,12}$
做法2:所以最终写法为:/(?!^\d{6,12}$)(?!^[a-z]{6,12}$)(?!^[A-Z]{6,12}$)^[\dA-Za-z]{6,12}$/
var regex = /(?!^\d{6,12}$)(?!^[a-z]{6,12}$)(?!^[A-Z]{6,12}$)^[\dA-Za-z]{6,12}$/;
console.log(regex.test("1234567"));
console.log(regex.test("1234567AZ"));
console.log(regex.test("1234567AZx"));
// false
// true
// true
主要参考来源: