正则表达式之字符串验证
正则表达式之字符串验证
在博文《正则表达式之数字验证》中我们探讨了数字的验证,比如身份证号码的验证、电话号码的验证等等,这些都是非常有用的;然而字符串的验证也是非常重要的。这篇博文我将和大家分享字符串的验证方法,如英文单词的验证、非单词字符串的验证、文件名称的验证以及网络常用元素的验证等等。 由于水平有限,有些知识点可能理解的不一定准确,希望如果大家发现错误后可以提出,在此表示感谢。
第一部分:5种英文单词验证
1.小写英文单词的验证
- 我们可以使用[a-z]+验证一个或多个小写英文单词,当然[a-z]{1,}亦是如此。但是这样验证的单词可能不是完整的,如对于字符串ad“”,它将匹配其中的ad。
- 为了解决上一个问题--即不能验证完整的单词,我们可以使用\b[a-z]+\b来验证。即通过元字符\b来指定英文单词的边界。
- \ba[a-z]*\b 可以验证以小写字母a开头的一到多个英文字母的单词。(注:限定符*表示0个或多个)
- \b[a-c][a-z]*\b可以验证以小写字母a或b或c开头的一个到多个英文字母的单词。
- \b[a-z]+(?:ing)\b 可以匹配以ing结尾的字符串,
- \b[a-z]{6} 可以验证长度为6的小写英文组成的字符串
注意:倒数第二个验证中的(?:ing), 虽然这里使用了(),即分组符号,但实际因为有?:,我们是不能进行反向引用的。 这里可以理解为我们仅需要将之看作一个整体,但是不希望被反向引用。
2.大写英文单词的验证
这里与小写英文单词的用法相同,我们只需要将上面的[a-z]替换成[A-Z]即可。
3.英文单词的分隔符验证
在英文文本中,各个英文单词被分隔符所分开。 分隔符即分开两两英文单词的符号。这些分隔符包括英文标点符号,空白符等等。
在分隔符中,又以英文标点符号居多,比如,(逗号) .(点号) ?(问号) :(冒号) ;(分号) '(单引号) !(感叹号) "(双引号) -(连接号) --(破折号) ()(小括号) [](中括号) {}(大括号) ...(省略号) `(所有格符号,又称反引号)。
如下面的正则表达式将验证这些英文标点符号分隔符:
[-,.?:;'"!`]|(-{2})|(\.{3})|(\(\))|(\[\])|({})
我为什么没有把所有的英文分隔符都放到字符类【】中去呢?这是因为对于--(破折号)...(省略号) ()(小括号) [](中括号) {}(大括号)这些分隔符或者会引起歧义不能正确表达出来,或者必须使用\来转义。
4.否定验证
- \b[A-GI-Z]+\b可以验证任何没有字母H的英文单词
- \b[A-GI-OQ-Z]\b可以验证任何没有字母H和P的英文单词
- \b[A-Z]*B[^P][A-Z]*\b可以验证任何在B之后没有P的英文单词。
- 但是为什么DAFB没有被匹配上呢?这是因为在B之后[^P]占了一个位置,即最后一定不能什么都没有。
5.具有相同特征的英文单词验证
a、使用\b([A-Z])\1[A-Z]*\b可以验证具有两个相同字母开头特征的英文单词。因为\1是在反向引用第一个分组。
b、使用\b([A-Z])[A-Z]*\1+[A-Z]*\b可以验证具有一个和首字母相同的字母特征的英文单词。
举例如下所示:
第二部分:6种非单词字符的验证
这一部分将介绍非单词字符串的验证,比如英文标点符号、中文标点符号、中文文本验证、特殊字符验证和密码验证。
1.英文标点符号的验证
即如下所示,在上面我们已经见过了:
[-,.?:;'"!`]|(-{2})|(\.{3})|(\(\))|(\[\])|({})
2.中文标点符号验证
中文标点符号也很多并且和英文标点符号很类似。如 ,(逗号) 。(句号) ?(问号) :(冒号) ;(分号) ‘’(单引号) !(感叹号) “”(双引号) —(连接号) ——(破折号) ……(省略号) ()(小括号) 【】(中括号) {}(大括号) 、(顿号) 《》(书名号) 等等。
于是我们可以通过下面的正则表达式来验证:
[,。?:;“” ‘’ !— …… 、]|(—{2})|(())|(【】)|({})|(《》)
其中(—{2})用来匹配破折号
3.中文文本验证
中文文本的验证比较简单,我们直接使用/w即可实现。如下图所示:
需要注意的是,如果没有u(注意观察灰色部分),则不能正确匹配,在http://www.regexpal.com/中我打开了unicode之后才可以正常匹配。
4.特殊字符验证
我们认为除了数字和字母之外的字符都是特殊字符,具体包括 、_ = \ [ ] ; ' ,. / ~ ! @ # $ % ^ & * ( ) + | ? > < “ :{ }。
使用以下正则表达式即可验证一个特殊字符:
[、_ =\ \\ [\ ] ; ' ,. / ~ ! @ # $ % ^ & * ( ) + | ? > < “ :{}]
其中\ [ ]需要通过使用\进行转义。
当然,如果需要验证长度至少为1、由特殊字符串组成的字符串,可直接在上面的正则表达式右边添加+即可。
5.密码验证
当用户登陆网站时,一般都需要用户输入用户名和密码,这时作为前端攻城狮的我们就需要进行验证了。当然,一般来说,密码的复杂程度越高,用户信息安全性越高。
密码字符可以包括数字、字母和特殊字符。因此在一个密码中可以只有数字或只有字母或只有特殊字符,也可以同时拥有其中的两种,或同时拥有其中的三种,显然,拥有的种类越多,则改密码越安全。
A 只包含数字的密码验证
这种形式的验证显然是非常简单的,其安全性也非常低。如下所示:
\d+
这样的表达式可以验证数字个数大于等于1的密码。而一般我们输入密码时有具体的要求,比如6到12位,我们可以按照下面的方式来验证。
\d{6,12}
B 只包含字母的密码验证
这也很简单,同样安全性较差。我们可以这样验证限制在6-12位的密码。
C 只包含特殊字符的密码验证
同样很简单,即
[、_=\\\[\];`',./~!@#$%^&*()+|?><":{}]{6,12}
此正则表达式验证的是6到12位的纯特殊字符的密码。
D 包含数字和字母的密码验证
这里似乎很简单,但实际上却不是,因为我们必须保证数字和字母同时都有。我的思考如下(如果大家觉得有更简洁的方式可以提出来):
[\da-zA-Z]*((\d+[a-zA-Z]+)|([a-zA-Z]+\d+))[\da-zA-Z]*
其中中间的分组(第一个分组)((\d+[a-zA-Z]+)|([a-zA-Z]+\d+))表示这个密码中必须是一个或几个数字后面跟着一个或几个字母 或者 一个或几个字母后面跟着一个或几个数字。如45dda或da564这种形式,如果一个密码时555或daf这肯定是不能匹配的。但这还是不够的,如果我们还希望在45dda的左边有字母,右边还有数字时,我们就需要在两边添加[\da-zA-Z]*了,其中*表示0个或多个。
E 包含数字和特殊字符的密码验证
在D的基础上,这里的正则表达式就很好写了,只需将字母的验证替换为特殊字符的验证即可,如下所示:
[\d、_=\\\[\];`',./~!@#$%^&*()+|?><":{}]*((\d+[、_=\\\[\];`',./~!@#$%^&*()+|?><":{}]+)|([、_=\\\[\];`',./~!@#$%^&*()+|?><":{}]+\d+))[\d、_=\\\[\];`',./~!@#$%^&*()+|?><":{}]*
F 包含字母和特殊字符的密码验证
在E的基础上,我们直接将其中的数字用字母来替换即可,如下所示:
[a-zA-Z_=\\\[\];`',./~!@#$%^&*()+|?><":{}]*(((a-zA-Z)+[_=\\\[\];`',./~!@#$%^&*()+|?><":{}]+)|([_=\\\[\];`',./~!@#$%^&*()+|?><":{}]+(a-zA-Z)+))[a-zA-Z_=\\\[\];`',./~!@#$%^&*()+|?><":{}]*
这里为什么验证不成功呢?? 如果有大神了解,希望可以给予指导,感激。
G 包含字母、数字和特殊字符的密码验证
如果三者都包含,那么此时密码的安全度是最高的。那么,怎么实现这样的密码验证呢?
思路同样的,即左右两边需要有字母、数字、字符串同时放在一个字符类里,中间的分组需要通过6次或运算即可实现。
第三部分:文件名称验证
每一个文件都有它自己的名称,该名称由两部分组成:文件名和文件扩展名。基于此,下面我们将要介绍 指定文件扩展名的验证、 指定文件名的验证、 包含指定字符串的文件全名的验证、 排除两端存在空白符的文件全名验证。
1. 指定文件扩展名的验证
假设我们验证文件扩展名为pdf的名称。验证时,文件名是长度至少为1的任意字符串。方法如下:
其中.+表示匹配长度至少为1、由非换行符组成的字符串。\.是为了对.进行转义。
2. 指定文件名的验证
假设我们验证文件名为javascript的名称。验证时,文件扩展名是长度至少为1的单词字符串。方法如下:
3. 包含指定字符串的文件全民名验证
这种验证方法是非常常见的,即一个文件全名中需要包含指定的字符串,比如一个文件全民中必须包含java这个字符串。验证方法如下:
4. 排除两端存在空白字符的文件全名验证
前面我们没有考虑到文件名两端存在空白字符的情况,然而,文件名的两端是不允许存在空白字符的。
(1)如果验证一个字符串不是以空白字符开头,可用(?!expression),即零宽度负预测先行断言。该断言可以指定此位置的后面不能匹配表达式expression,于是验证如下:
(2) 如果验证一个字符串不是以空白字符结束,可用(?<!expression),即零宽度负回顾后发断言,它断言自身位置的前面不能匹配表达式expression,于是验证如下:
^.+(?<! )\.\w+$
(3) 结合上面两种情况,即可得到文件名两端都不存在空格的验证如下所示:
^(?! ).+(?<! )\.\w+$
第四部分:电子邮件、HTTP/FTP地址验证
这四个都是网络的常用元素,尤其是电子邮件的验证用的很多。
1.电子邮件验证
我们知道常见的电子邮箱有163 邮箱 126 邮箱 QQ 邮箱 Gmail邮箱 雅虎邮箱 Hotmail 新浪邮箱 139 邮箱 TOM邮箱 21CN邮箱 搜狗邮箱 189邮箱 188财富邮亿邮 Yeah邮箱 搜狐邮箱 Foxmail等等,但是他们的特点都十分类似,如qq邮箱地址:1843021156@qq.com,Gmail邮箱地址 zhuzhenwei789@gmail.com等等。当然上述的邮箱是大型公司提供的免费邮箱。 公司还可以有自己的企业邮箱。比如123456abcd@facai.com.cn等等。
综上所述,我们可以看出邮箱一般是由名称、字符@和域名后缀组成。
根据邮箱的特点,我们便可以使用下面的正则表达式来验证电子邮件地址:
^\w+@(\w+\.)+\w+
效果如下所示:
当然,下面这种方法(思路)也是一样的:
^\w+@\w+(\.\w+)+
上面的说法是有问题的,这里更正,应该是
^[\w.]+@(\w+\.)+\w+
因为前面的名称也有可能是有小数点的。
2.HTTP、FTP地址验证
HTTP地址一般是以字符串"http://"或"https:"开头的字符串。它可以被. / ? & % =分割。 如http://www.cnblogs.com、https://www.baidu.com/s?wd=谷歌&rsv_spt=1、http://cn.bing.com/search?q=javascript等等。而FTP和HTTP的唯一区别在于开头是FTP而不是HTTP或HTTPS。
于是可知验证表达式如下:
((http|ftp|https)://)(([a-zA-Z0-9\._-]+\.[a-zA-Z]{2,6})|([0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}))(:[0-9]{1,4})*(/[a-zA-Z0-9\&%_\./-~-]*)?
首先该正则表达式匹配的字符串必须以http://、https://、ftp://开头;
其次该正则表达式能匹配URL或者IP地址;(如:http://www.baidu.com 或者 http://192.168.1.1)
然后该正则表达式能匹配到URL的末尾,即能匹配到子URL;(如能匹配:http://www.baidu.com/s?wd=a&rsv_spt=1&issp=1&rsv_bp=0&ie=utf-8&tn=baiduhome_pg&inputT=1236)
最后该正则表达式能够匹配端口号;
结语:
这篇文章写完才发现对正则表达式的理解还不够透彻,比如字母、数字、特殊字符构成的密码验证还有些问题待解决,最后HTTP和FTP的验证我觉得写的也过于繁杂,并没有解决所有问题。所以如果大家有什么好的建议希望可以指教,在此表示感谢。
注:原创文章,如需转载,请注明出处,博客地址:http://www.cnblogs.com/zhuzhenwei918/p/6202932.html