正则表达式的技巧总结

正则表达式在现在web的应用当中,如表单验证,url解析等,应用非常方便,比起普通的字符串解析性能上也高出不少。
这里就做一些关于正则表达式通用技巧的个人小总结,正则的入门可以参考以下网址内容
http://www.regexlab.com/zh/regref.htm
http://w3school.com.cn/js/jsref_obj_regexp.asp

1. 一些常用的元字符.
\w : 查找单词字符,包含字母数字及下划线,相当于[A-Za-z0-9_];
\d : 查找数字,相当于[0-9]
\s : 查找空白字符
\n : 查找换行符
. : 点号代表除换行符及行结束符外所有字符

2. 验证完整字符串,这在表单验证中常用到,例子如下:

var str = '18636200607';
var str2 = '10010';
var reg = /^\d{11}$/;
console.log(reg.test(str)); // return true;
console.log(reg.test(str2)); // return false;

这里的头尾的^$即是限定匹配的必须是整个字符串,而不是其中一部分,这对于表单验证里验证完整的合法输入很有用。

3. 验证一个完整的单词,可以用到\b,例子如下:

var str = 'hello world!';
var str2 = 'helloworld!';
var reg = /\bhello\b/;
console.log(reg.test(str)); //return true
console.log(reg.test(str2)); //return false

这里\b作为单词的边界条件进行判断,与^$夹着字符串相似,但\b夹的是单个单词

4. 捕获型分组与非捕获型分组
捕获型分组是小括号包围起来的一个分组表达式,里面匹配到的内容可以在之后调用,例子如下:

var str = '1234haha';
var reg = /(\d+)\w+/;
var result = reg.exec(str);
console.log(result[0]); //return '1234haha'
console.log(result[1]); //return '1234'

正则对象的exec方法与test不同,它如果匹配不成功返回null,成功则返回一个数组对象,[0]包含匹配到的完整字符串,[1][2]…等等则保存着各个子表达式里所捕获的内容(即小括号里获取的字符串);
小括号在正则里还有一个用处则是起到分组的作用
如: (abcd){4}
此表达式表示abcd整个字符串重复4次才能匹配成功
但小括号同时也影响了exec方法返回的捕获数组内容,
此时如果不希望捕获内容影响,可以使用非捕获分组,非捕获分组格式是(?:…..);
如: (?:abcd){4}
此时小括号里的内容只会起到分组的作用,并不会捕获内容。

5. 方括号与分组表达式的或结构
方括号里的内容只会匹配单个字符,
例如 [1234] 只会匹配1234里的一个字符,如果希望匹配的是一个字符串可以使用非捕获型分组来达成目的
而或结构的分组表达式 (?:12|34) 会匹配12 或 34这两个字符里的其中一组。
示例代码:

var str = '1234';
var reg = /[1234]/;
var reg2 = /(?:12|34)/;
console.log(reg.exec(str)[0]); //retrun '1'
console.log(reg2.exec(str)[0]); //return '12'

6. 贪婪模式与非贪婪模式
\w+ 在匹配字符串 ‘hello’ 时会匹配整个字符串,此时为贪婪模式
\w+? 在匹配时 则只匹配 ‘h’单个字符串,此时为非贪婪模式
也就是说在量词(*, +, ?, {5, })后面加个?即形成非贪婪模式,会尽可能在不影响匹配成功的情况下,少匹配字符
示例代码:

var str = 'hello';
var reg = /\w+/;
var reg2 = /\w+?/;
console.log(reg.exec(str)[0]); //retrun 'hello'
console.log(reg2.exec(str)[0]); //return 'h'

7. 反向引用
捕获型分组里捕获的内容在三种情况下可以被引用
第一是exec方法回复的数组里,从[1]开始
第二是test或exec方法执行后,RegExp.$1开始之后存储捕获内容
第三则是在正则表达式里的反向引用,如\1 \2这种形式
看下例子:

var str = '<td>这里是td</td>';
var reg = /<(\w+)>.*<\/\1>/;
console.log(reg.test(str)); // return true

此处正则表达式里\1则是引用了前面的捕获型分级(\w+)的内容

8. 正向预搜索及不匹配
预搜索与^$\b一样本身不匹配内容,只是提供一个判断
看下例子:

var str = 'HelloWorld';
var reg = /Hello(?=World)/;
var reg2 = /Hello(?!World)/;
console.log(reg.test(str)); // return true
console.log(reg2.test(str)); //return false

(?=…)代表前面要匹配的字符后面必须带有指定的字符才能匹配成功
(?!…)则相反,代表不包含指定的字符
javascript不支持反向预搜索,这里就不介绍了

9. 正则对象的方法
RegExpObject.test 方法:
这是表单验证中常用到的方法,如果匹配成功返回true,反之false

RegExpObject.exec 方法:
exec方法很强大,它基本提供了所有所需要的信息
返回的是一个数组,数组的[0]存放的是匹配到的完整字符串,[1][2]开始存放的是捕获型分组(也就是正则里的小括号包围的内容)捕获到的字符串,
该数组还包含额外两个属性index及input; index标识的是匹配结果的字符串位置,input标识的是正则表达式
其实exec最强大的地方是在于,对于带g全局标识的正则表达式(如/\w+/g),在每次执行exec的时候,都会将正则对象的lastIndex设置为前一个匹配到的字符串的最后一个位置
换句话说,你就可以利用这个特性进行整个字符串的遍历,并配合捕获型分组,就可以得到你想要的字串内容
看如下例子

//解析url
var url = 'http://www.taobao.com/?ver=1.0&q=search';
var reg = /(\w+)=([^&]*)/g;
var obj = {};
var result;
while(result = reg.exec(url)){
    obj[result[1]] = result[2];
}
console.log(obj); //return {ver:'1.0', q:'search'}

以上就可以遍历正则匹配整个字符串,配合捕获分组就可以得到你想要的字串了

String.match 方法 :
如果正则表达式不带g全局标识,字符串的match方法与正则对象的exec对象相似,只进行一次匹配,返回一个数组,[0]存放的是完整匹配字串,[1]以后存放捕获分组的内容
如果正则表达式带g全局标识,则match方法回返的内容大不一样,也是一个数组,但是是从[0]开始各个存放匹配到的完整匹配字串,就不会再存放捕获分组的内容了
有时这在简单匹配整个字串的时候比起exec简便些
看下例子:

var str = '1: 哈哈,2: 呵呵, 3: 嘿嘿';
var reg = /\d:/g;
console.log(str.match(reg)); //return ['1:', '2:', '3:']

以上直接回返匹配到的结果数组

String.replace 方法:
字符串的replace方法带两个参数,第一个参数是查找匹配的字符串,第二个参数是要替换成的内容,也可以是个function匿名函数
如果是正则替换方式,则第二个参数里的$有特殊的含义,$1 $1…代表的是之前正则表达式里的捕获分组得到的字串,$&代表的是匹配得到的完整字串,$`代表匹配字串左侧的文本,$’代表匹配字串右侧的文本

看下面个例子:

var str = 'hello world!';
var reg = /(\w+)\s(\w+)/;
str = str.replace(reg, '$2 $1');
console.log(str); //return 'world hello!'

这里利用到$1 $2的捕获分组的内容。

再看个例子:

var str = 'background-color';
var reg = /-(\w)/g;
str = str.replace(reg, function(w, s){
    return s.toUpperCase();
});
console.log(str); // return 'backgroundColor'

对于加g的正则表达式,replace方法会循环执行替换操作,replace方法里的第二个参数如果是function,则function的第一个参数是完整的正则匹配字串,第二个参数开始则是捕获分组得到的字串。

String.split方法及String.search方法较为简单,可参考相关资料

参考资料:
http://www.regexlab.com/zh/regref.htm
http://w3school.com.cn/js/jsref_obj_regexp.asp

共3条评论

  1. Pingback: ♂ヤ〇點ㄋ↙ » Blog Archive » 正则表达式的技巧总结

  2. 慢慢回归..Cloud IDE..像我这种只能沦为被取笑的对象..整天在家里摸摸摸…

  3. 博主这篇文章写的很不错,观点很认同啊,以后会经常来看看。http://goo.gl/e4P2u

发表评论

>>
后台管理 工具库 RSS 微博 简历