http://www.ipc.me/regular_expression_07681.html
文章错误:
1 字符集的一些应用 第二个正则少了一个左方括号。
2 字符集的元字符 /[]x]/中的第一个]左边少了一个转义符,在这种情况下转义符还是不能省略的。
扩展
1 回车符 换行符 http://www.cnblogs.com/yunf/archive/2011/04/20/2021830.html
表达式引擎
正则表达式引擎室一种可以处理正则表达式的软件,通常是大程序的一部分,不用的表达式互不兼容(JDK .NET)。
两种类型:文本导向(text-dereced/DFA) 和 正则导向 (regex-directed/NFA)
主流是NFA,因为(惰性/lazy quantifiers)以及(反向引用/backreferences)只能在正则NFA中实现。
分辨两种引擎的方法:
/reg|reg not/ 如果匹配到reg,那么是正则导向;如果是reg not,是文本导向。
因为正则导向引擎总是返回最左边的匹配,猴急。
特殊字符(11)
[ ] () ^ $ + \ | . ?
2个括号 4 6 12 (\) shift左边2个
在一些预编译(C++)中,\ 数量加倍
不显示的字符
\t tab(0x09)
\r 回车(0x0D)
\n 换行(0x0A)
显示的字符,是敲“ABC123”是可以看到的,那换行/回车/Tab 键 是看不到的。
连字符 -
可以指定范围,如[0-9a-fxA-FX]
反字符 [^]
q[^u]不会匹配iraq,会匹配 Iraq is a country,因为[]必须要匹配一个字符
如果你只想匹配一个q,条件是q后面有一个不是u的字符,我们可以用后面将讲到的向前查看来解决?
在[]中, 有 4 个元字符需要转义 ] \ ^ - 其他元字符不需要转义,但是其中 2 个元字符(^-)的转义符不是必须的
只要将他们放在一个不可能使用到他们的特殊位置,这样子可以增加可读性。
例如^只要不放到 [ 的后面,就可以不用转义符。[x^] [-x]
常用的字符集简写
\d 0-9 取反\D
\w A-Za-z0-9 取反\W
\s 空白字符 空格符 Tab符 回车\r 换行\n 取反 \S
[0-9]+ 仅仅想重复匹配那个数字 向后引用?
注意贪婪
?* + 都是贪婪的,会尽可能的重复前导字符。(?会尽可能匹配一次)
例子:
var reg = /<.+>/;// /<[^>]+>/ 或者 /<.+?>/
var str ='This is a <EM>first</EM> test';
console.log(str.match(reg));
表达式<.+会贪婪匹配到字符串结束(最后还有个换行符,'.'不匹配换行符,(换行符是怎么出来的?)),然后表达式的剩余 部分 > 去匹配换行符,匹配不成功,然后进行回溯(!!),<.+ 会丢掉匹配的最后一个字符 让>去匹配,直到成功为止。最后 停留在<EM>first</EM。匹配结果是<EM>first</EM>。
'+'的贪婪性使得表达式匹配到最左边的最长的匹配。
不管是惰性匹配还是贪婪匹配,都会进行回溯,会影响效率。
. == [^\r\n](Window)不匹配换行符的历史原因:为早期使用正则表达式的工具是基于行的。它们都是一行一行的读入一个文件 ,将正则表达式分别应用到每一行上去。在这些工具中,字符串是不包含新行符(\n)的(历史)。现代的工具和语言能够将正则 表达式应用到很大的字符串甚至整个文件上去。
单行模式,将整个文件一并读入,此时.匹配新行符,只影响.的匹配范围。
***
多行模式和单行模式没有什么关系,只是名字相似。
多行模式下,只影响^ 和 $ 的匹配范围
^ 可以匹配字符串开头(字符串的开始位置),也可以匹配行的开头(即换行符\n之后的位置)
$ 可以匹配字符串结尾(字符串的结束位置), 也可以匹配行的结尾(即换行符\n之前的位置)
Regex.Match(“string”,”regex”,RegexOptions.SingleLine)可以激活单行模式。
var reg = /(?:0[1-9]|1[0-2])[-/.](?:0[1-9]|[1-2]\d|3[01])/;//(?:)匹配但是不获取,经常和| 配合使用
var str ='12/01';
console.log(str.match(reg));
字符串开始和结束的锚定 (^$)
^$ 和一般的表达式符号不用,他不匹配任何字符,他会匹配字符之前或者之后的位置。
“first line\n\rsecond line”其中的 \n\r 在WINDOWS下是换行回车的标志,正则表达式引擎提供一个选项可以是扩展 '^'
绝对锚定
\A 和 \Z 只匹配整个字符串的开始位置和结束位置,即使你使用了多行模式。
单词边界\b <=> \B
也是一种锚
1)在字符串的第一个字符前的位置(如果字符串的第一个字符是一个“单词字符”)
2)在字符串的最后一个字符后的位置(如果字符串的最后一个字符是一个“单词字符”)
3)在一个“单词字符”和“非单词字符”之间,其中“非单词字符”紧跟在“单词字符”之后
4) 在一个“非单词字符”和“单词字符”之间,其中“单词字符”紧跟在“非单词字符”后面
*单词字符 指 \w == [a-zA-Z0-9]
组()与 后向引用
()匹配后生成组,\0代表整个背匹配的结果,用\N来引用剩余的,()经常会和|配合使用,用来限制|的范围,(?: pattern)不 获取匹配结果...
<([A-Z][A-Z0-9]*)[^>]*>.*?</\1> 可以用来匹配标签。
注意点:
后向引用不能用于他自身,([abc]\1)
后向引用不能用于字符集内部 (a)[\1b]
当对组使用重复操作符时,缓存里后向引用内容会被不断刷新,只保留最后匹配的内容。
模式
i 大小写不敏感
s 单行模式
m 多行模式
(?i)te(?-i)st 能匹配TEst 原因就是?i开启了不敏感,随后又关闭了敏感,变得敏感了。