当前位置:编程学习 > 网站相关 >>

正则基础之  单词边界

一、 概述


“”匹配单词边界,不匹配任何字符。
“”匹配的只是一个位置,这个位置的一侧是构成单词的字符,另一侧为非单词字符、字符串的开始或结束位置。“”是零宽度的。
 基本上所有的资料里都会说“”是单词边界,但是关于“单词”的范围却是少有提及。通常情况下,正则表达式中所谓的“单词”,就是由“w”所定义的字符所组成的子串。
“”表示所在位置的一侧为单词字符,另一侧为非单词字符、字符串的开始或结束位置,也就相当于
(?<!w)(?=w)|(?<=w)(?!w)
思考:以下写法为什么不等价于“”
(?<=W)(?=w)|(?<=w)(?=W)


二、w的范围


即然涉及到“w”,那就要先考察一下它的范围。
在支持ASCII码的语言中,如JavaScript,“w”等价于[a-zA-Z0-9_] ;
在支持Unicode的语言中,如.NET,默认情况下,“w”除可以匹配[a-zA-Z0-9_]外,还可以匹配一些Unicode字符集,如汉字,全角数字等等。
几乎所有常见的语言都遵循这样一个规律,只有Java是个例外。在Java中,“w”的表现是比较奇怪的,Java是支持Unicode的,但Java的正则中的“w”却是等价于[a-zA-Z0-9_]

的。
先来看一下“w”在几种语言中匹配的例子


JavaScript

<script language="javascript">
var str = "abc_123中文_d3=efg汉字%";
var reg = /w+/g;
var arr = str.match(reg);
if(arr != null)
{
for(var i=0;i<arr.length;i++)
{
document.write(arr[i] + "<br />");
}
}
</script>
//JavaScript中输出
abc_123
_d3
efg

C#

string test = "abc_123中文_d3=efg汉字%";
MatchCollection mc = Regex.Matches(test, @"w+");
foreach (Match m in mc)
{
richTextBox2.Text += m.Value + " ";
}
//C#中输出
abc_123中文_d3
efg汉字

Java

String test = "abc_123中文_d3=efg汉字%";
String reg = "\w+";
Matcher m = Pattern.compile(reg).matcher(test);
while(m.find())
{
System.out.println(m.group());
}
//Java中输出
abc_123
_d3
efg

可以看到,“w”在Java中的输出和JavaScript中是一样的,都是只支持ASCII字符。

 
三、的范围

常见语言中“w”的范围确定了,那么是不是可以认为“”的匹配范围与“w”也是一致的呢?
再看下下面的例子:
源字符串:abc_123中文_d3=汉字efg
正则表达式: ..


JavaScript

<script language="javascript">
var str = "abc_123中文_d3=efg汉字%";
var reg = /../g;
var arr = str.match(reg);
if(arr != null)
{
for(var i=0;i<arr.length;i++)
{
document.write(arr[i] + "<br />");
}
}
</script>
//JavaScript中输出
3中
文_
3=
g汉

C#

string test = "abc_123中文_d3=efg汉字%";
MatchCollection mc = Regex.Matches(test, @"..");
foreach (Match m in mc)
{
richTextBox2.Text += m.Value + " ";
}
//C#中输出
3=
字%

Java

String test = "abc_123中文_d3=efg汉字%";
String reg = ".\b.";
Matcher m = Pattern.compile(reg).matcher(test);
while(m.find())
{
System.out.println(m.group());
}
//Java中输出
3=
字%

可以看到,Java的输出和.NET是一致的,“”在Java中是支持Unicode的。
所以总的来说,Java中的“w”是很奇怪的,而“”是与其它语言表现一致的,在使用时需要注意。


四、 应用场景


4.1 基础应用
“”一般应用在需要匹配某一单词字符组成的子串,但这一字符不能包含在同样由单词字符组成的更长的子串中。
比如要替换掉一段英文中的单词“to”,而“today”显然不在替换的范围内,所以正则可以用“to”来限定。
用得比较多的场景是在HTML标签的匹配中,用以区分相互包含的标签,比如要过滤掉<b>、</b>、<p…>、<img…>等标签,但要保留<br />标签,正则可以写成“<(/?b|p|img)

[^>]*>”。
举例:统计以“,”分割的元素中“3”的个数
string test = "137,1,33,4,3,6,21,3,35,93,2,98";
int count = Regex.Matches(test, @"3").Count; //结果:2


4.2特殊情况
“”用在正则中,通常情况下都是表示单词边界的,只有在字符组中,它表示的是退格键,即 [a-z] 此处的“”表示的是退格键,而不是单词边界

补充:综合编程 , 其他综合 ,
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,