正则表达式之零宽断言详解
0. 概念
-
零宽 Zero-width : 表示该子正则表达式本身并不产生匹配字符, 也不消耗输入字符串, 等同效果为宽度零的字符串.
-
lookahead: 表示从当前匹配位置之后匹配断言表达式
-
lookbehind: 表示从当前匹配位置之前匹配断言表达式
-
Positive: 表示条件满足断言匹配表达式时为匹配
-
Negative: 表示必须条件不满足断言匹配表达式时为匹配
-
总结:
表达式 定义 (?=exp) 正预测先行断言 (?!exp) 负预测先行断言 (?<=exp) 正回顾后发断言 (?<!exp) 负回顾后发断言
1. 零宽度正预测先行断言 Zero-width positive lookahead (?=exp)
1.1 零宽度正预测先行断言 (?=.+and.+)
“cats, dogs and some mice.”
\b\w+\b(?=.+and.+)
# 输出结果: "cats", "dogs"
-
解析正则表达式
\b\w+\b(?=.+and.+)
的作用:\b
:匹配单词边界。\w+
:匹配一个或多个单词字符(字母、数字或下划线)。\b
:再次匹配单词边界。(?=.+and.+)
:正预测先行断言,表示在当前位置之后(lookahead)
必须(positive)跟着任意字符(.+
),然后是 “and”,再跟着任意字符(.+
)。
-
综上所述:这个正则表达式会匹配单词边界内的一个或多个单词字符的字符串,并且该字符串后面必须有任意字符,接着是 “and” 及其后的任意字符。
-
示例句子 “cats, dogs and some mice.” 中的匹配情况:
cats
:匹配,因为cats
后面有and
且与and
之间还有其他任意字符dogs
:匹配,因为dogs
后面有and
且与and
之间还有其他任意字符and
:不匹配,因为and
后面没有and
some
:不匹配,因为some
后面没有and
mice
:不匹配,因为mice
后面没有and
-
匹配结果如下:
cats
dogs
2. 零宽度负预测先行断言 Zero-width negative lookahead (?!exp)
2.1 零宽度负预测先行断言 (?!.+and.+)
“cats, dogs and some mice.”
\b\w+\b(?!.+and.+)
# 输出结果: "and", "some", "mice"
-
解析正则表达式
\b\w+\b(?!.+and.+)
的作用:\b
:匹配单词边界。\w+
:匹配一个或多个单词字符(字母、数字或下划线)。\b
:再次匹配单词边界。(?!.+and.+)
:负预测先行断言,表示在当前位置之后(lookahead)
不能(negative)有"任意字符(.+
),然后是 “and”,再跟着任意字符(.+
)"。
-
综上所述:这个正则表达式会匹配单词边界内的一个或多个单词字符的字符串,并且该字符串后面不能有任意字符,接着是 “and” 及其后的任意字符。
-
示例句子 “cats, dogs and some mice.” 中的匹配情况:
cats
:不匹配,因为cats
后面有 单词and
dogs
:不匹配,因为dogs
后面有 单词and
and
:匹配,因为and
后面没有单词and
some
:匹配,因为some
后面没有单词and
mice
:匹配,因为mice
后面没有单词and
-
匹配结果如下:
and
some
mice
3. 零宽度正回顾后发断言 Zero-width positive lookbehind (?<=exp)
3.1 零宽度正回顾后发断言 (?<=.+and.+)
“cats, dogs and some mice.”
\b\w+\b(?<=.+and.+)
# 输出结果: "some", "mice"
-
解析正则表达式
\b\w+\b(?<=.+and.+)
的作用:\b
:匹配单词边界。\w+
:匹配一个或多个单词字符(字母、数字或下划线)。\b
:再次匹配单词边界。(?<=.+and.+)
:正回顾后发断言,表示在当前位置之前(lookbehind)
必须(positive)有任意字符(.+
),然后是 “and”,再跟着任意字符(.+
)。
-
综上所述:这个正则表达式会匹配单词边界内的一个或多个单词字符的字符串,并且该字符串前面必须有任意字符,接着是 “and” 及其后的任意字符。
-
示例句子 “cats, dogs and some mice.” 中的匹配情况:
cats
:不匹配,因为cats
前面没有单词and
dogs
:不匹配,因为dogs
前面没有单词and
and
:不匹配,因为and
前面与单词and
没有间隔一个字符some
:匹配,因为some
前面有单词and
mice
:匹配,因为mice
前面有单词and
-
匹配结果如下:
some
mice
3.2 零宽度正回顾后发断言 (?<=.+and.*)
“cats, dogs and some mice.”
\b\w+\b(?<=.+and.*)
# 输出结果: "and", "some", "mice"
-
解析正则表达式
\b\w+\b(?<=.+and.*)
的作用:\b
:匹配单词边界。\w+
:匹配一个或多个单词字符(字母、数字或下划线)。\b
:再次匹配单词边界。(?<=.+and.*)
:正回顾后发断言,表示在当前位置之前必须有任意字符(.+
),然后是 “and”,再跟着任意数量的任意字符(.*
)。
-
综上所述:这个正则表达式会匹配单词边界内的一个或多个单词字符的字符串,并且该字符串前面必须有任意字符,接着是 “and” 及其后的任意数量的字符。
-
示例句子 “cats, dogs and some mice.” 中的匹配情况:
cats
:不匹配,因为cats
前面的部分是空的,不符合.+and.*
。dogs
:不匹配,因为dogs
前面的部分是cats,
,不符合.+and.*
。and
:匹配,因为and
前面的与单词and
匹配, 且间隔了任意数量(0个)字符.*
some
:匹配,因为some
前面的部分是cats, dogs and
,符合.+and.*
。mice
:匹配,因为mice
前面的部分是cats, dogs and some
,符合.+and.*
。
-
匹配结果如下:
and
some
mice
4. 零宽度负回顾后发断言 Zero-width negative lookbehind (?<!exp)
4.1 零宽度负回顾后发断言 (?<!.+and.+)
“cats, dogs and some mice.”
\b\w+\b(?<!.+and.+)
# 输出结果: "cats", "dogs", "and"
-
解析正则表达式
\b\w+\b(?<!.+and.+)
的作用:\b
:匹配单词边界。\w+
:匹配一个或多个单词字符(字母、数字或下划线)。\b
:再次匹配单词边界。(?<!.+and.+)
:负回顾后发断言,表示在当前位置之前不能有任意字符(.+
),然后是 “and”,再跟着任意字符(.+
)。
-
综上所述:这个正则表达式会匹配单词边界内的一个或多个单词字符的字符串,并且该字符串前面不能有任意字符,接着是 “and” 及其后的任意字符。
-
示例句子 “cats, dogs and some mice.” 中的匹配情况:
cats
:匹配,因为cats
前面没有 “and” 及其后的任意字符。dogs
:匹配,因为dogs
前面没有 “and” 及其后的任意字符。and
:匹配,因为and
前面没有 “and” 及其后的任意字符。some
:不匹配,因为some
前面有 "dogs and "。mice
:不匹配,因为mice
前面有 "and some "。
-
匹配结果如下:
cats
dogs
and
4.2 零宽度负回顾后发断言 (?<!.+and.*)
“cats, dogs and some mice.”
\b\w+\b(?<!.+and.*)
# 输出结果: "cats", "dogs"
-
解析正则表达式
\b\w+\b(?<!.+and.*)
的作用:\b
:匹配单词边界。\w+
:匹配一个或多个单词字符(字母、数字或下划线)。\b
:再次匹配单词边界。(?<!.+and.*)
:负回顾后发断言,表示在当前位置之前不能有任意字符(.+
),然后是 “and”,再跟着任意数量的任意字符(.*
)。
-
综上所述:这个正则表达式会匹配单词边界内的一个或多个单词字符的字符串,并且该字符串前面不能有任意字符,接着是 “and” 及其后的任意数量的字符。
-
示例句子 “cats, dogs and some mice.” 中的匹配情况:
cats
:匹配,因为cats
前面的部分是空的,不符合.+and.*
。dogs
:匹配,因为dogs
前面的部分是cats,
,不符合.+and.*
。and
:不匹配,因为and
前面的部分是cats, dogs
,但与自身符合.+and.*
。some
:不匹配,因为some
前面的部分是cats, dogs and
,符合.+and.*
。mice
:不匹配,因为mice
前面的部分是cats, dogs and some
,符合.+and.*
。
-
匹配结果如下:
cats dogs