在javascript中使用单词边界匹配字母数字和非字母数字字符的正则表达式

时间:2010-11-18 13:54:40

标签: javascript regex alphanumeric

我试图使用JavaScript和正则表达式突出显示一组关键字,我遇到一个问题,我的关键字可能包含文字和特殊字符,如@text #number等。我使用字边界来匹配和替换整个字而不是一个部分词(包含在另一个词中)。

var pattern = new regex('\b '( + keyword +')\b',gi);

此处此表达式匹配整个关键字并突出显示它们,但是如果任何关键字如“number:”没有突出显示。

我知道\bword\b匹配单词边界,而特殊字符是非字母数字字符,因此与上述表达式不匹配。 你能让我知道我可以使用什么正则表达式来实现上述目的。

==的更新 ==

对于上述内容,我尝试了Tim Pietzcker对以下正则表达式的建议,

expr: (?:^|\\b|\\s)(" + keyword + ")(?:$|\\b|\\s)

以上似乎可以让我使用字母数字和非字母数字字符匹配整个单词,但是只要关键字在没有空格的关键字之前或之后具有连续的html标记,它就不会突出显示该关键字(例如社会保障 * 号码: < br> *) 我尝试了以下正则表达式,但它取代了关键字

之前的html标记
expr: (?:^|\b|\s|<[^>]+>)number:(?:$|\b|\s|<[^>]+>) 

此处有关键字数字:,其中< br >(有意为br标签添加空间,以避免浏览器解释标签)接下来没有空格,用关键字突出显示。

你能否建议一个表达式忽略整个单词的连续html标签,包括字母数字和非字母数字字符。

6 个答案:

答案 0 :(得分:2)

好的,所以你有两个问题:JavaScript不支持lookbehind,而\b只能找到字母数字字符和非字母数字字符之间的边界。

第一个问题: 究竟是什么构成了关键字的字边界?我的猜测是它必须是\b边界或空格。如果是这种情况,您可以搜索

"(?:^|\\b|\\s)(" + keyword + ")(?:$|\\b|\\s)"

当然,像@number#这样的关键字周围的空白字符也会成为匹配的一部分,但也许突出显示这些并不是一个问题。在其他情况下,我。即如果存在可以匹配的实际单词边界,则空格不会成为匹配的一部分,因此在大多数情况下它应该可以正常工作。

您感兴趣的实际单词将在反向引用#1中,因此如果您可以单独突出显示,甚至更好。

编辑: 如果在关键字之后/之前可能出现除空格之外的其他字符,那么我认为您唯一可以做的事情(如果您遇到JavaScript)是:

  1. 检查您的关键字是否以alnum字符开头。
  2. 如果是,请在您的正则表达式前加\b
  3. 检查您的关键字是否以alnum字符结尾。
  4. 如果是,请将\b附加到正则表达式。
  5. 因此,对于keyword,请使用\bkeyword\b;对于number:,请使用\bnumber:;对于@twitter,请使用@twitter\b

答案 1 :(得分:1)

我们需要查找两边都有空格字符的子字符串。如果JavaScript支持lookbehind,这将看起来像:

var re = new RegExp('(?<!\\S)' + keyword + '(?!\\S)', 'gi');

虽然这不起作用(但在Perl和其他脚本语言中)。相反,我们需要包括领先的空白字符(或字符串的开头)作为匹配的开始部分(并且可选地将我们真正想要的内容捕获到$ 1):

var re = new RegExp('(?:^|\\s)(' + keyword + ')(?!\\S)', 'gi');

只要认为任何匹配开始的真实位置 .index返回的re.exec(string)属性所返回的内容之后的一个字符,如果您要访问匹配的字符串,则需要删除带有.slice(1)的第一个字符,或者只需访问捕获的内容。

答案 2 :(得分:0)

也许你想要做的是

'\b\W*(' + keyword + ')\W*\b'

答案 3 :(得分:0)

Lookahead和lookbehind是你的答案:"(?=<[\s^])" + keyword + "(?=[\s$])"。括号中的位不包括在匹配中,因此请包含其中关键字中不允许的任何字符。

答案 4 :(得分:0)

正如蒂姆正确指出的那样,\b是棘手的事情,其工作方式与人们通常认为的工作方式不同。阅读this answer了解有关此事的更多详情,以及您可以采取的措施。

简而言之,这是左边界:

(?(?=\w)(?<!\w)|(?<!\W))

这是右边界:

(?(?<=\w)(?!\w)|(?!\W))

人们总是认为有空间,但没有。但是,既然您已经了解了真正的定义,那么很容易将它们构建到它们中。在上面的两种模式中,可以在\w\W的交换中换出\s\S。或者可以在其他块中添加空白感知。

答案 5 :(得分:0)

试试这个应该有用......

var pattern = new regex(@"\b"+Regex.escape(keyword)+@"\b",gi);