112

我有一个正则表达式,用于查找给定内容块中的所有单词,不区分大小写,这些单词包含在存储在数据库中的词汇表中。这是我的模式:

/($word)/i

问题是,如果我使用/(Foo)/ithen 这样的词Food得到匹配。单词的两边都需要有空格或单词边界。

如何修改我的表达式以仅匹配Foo句子开头、中间或结尾的单词?

4

7 回答 7

156

使用单词边界:

/\b($word)\b/i

或者,如果您在 Sinan Ünür 的示例中搜索“SPECTRE”:

/(?:\W|^)(\Q$word\E)(?:\W|$)/i
于 2009-11-17T19:51:14.593 回答
67

要匹配任何整个单词,您将使用该模式(\w+)

假设您使用的是 PCRE 或类似的东西:

在此处输入图像描述

以上截图取自此现场示例:http ://regex101.com/r/cU5lC2

将命令行上的任何整个单词与(\w+)

我将在Ubuntu 12.10上使用phpsh 交互式 shell ,通过preg_match方法演示PCRE 正则表达式引擎

启动phpsh,将一些内容放入变量中,匹配word。

el@apollo:~/foo$ phpsh

php> $content1 = 'badger'
php> $content2 = '1234'
php> $content3 = '$%^&'

php> echo preg_match('(\w+)', $content1);
1

php> echo preg_match('(\w+)', $content2);
1

php> echo preg_match('(\w+)', $content3);
0

preg_match 方法使用 PHP 语言中的 PCRE 引擎来分析变量:,$content1$content2模式。 $content3(\w)+

$content1 和 $content2 至少包含一个单词,$content3 不包含。

将命令行上的多个文字单词与(dart|fart)

el@apollo:~/foo$ phpsh

php> $gun1 = 'dart gun';
php> $gun2 = 'fart gun';
php> $gun3 = 'farty gun';
php> $gun4 = 'unicorn gun';

php> echo preg_match('(dart|fart)', $gun1);
1

php> echo preg_match('(dart|fart)', $gun2);
1

php> echo preg_match('(dart|fart)', $gun3);
1

php> echo preg_match('(dart|fart)', $gun4);
0

变量 gun1 和 gun2 包含字符串 dart 或 fart。gun4 没有。然而,寻找单词fart匹配可能是个问题farty。要解决此问题,请在正则表达式中强制执行单词边界。

将命令行上的文字单词与单词边界匹配。

el@apollo:~/foo$ phpsh

php> $gun1 = 'dart gun';
php> $gun2 = 'fart gun';
php> $gun3 = 'farty gun';
php> $gun4 = 'unicorn gun';

php> echo preg_match('(\bdart\b|\bfart\b)', $gun1);
1

php> echo preg_match('(\bdart\b|\bfart\b)', $gun2);
1

php> echo preg_match('(\bdart\b|\bfart\b)', $gun3);
0

php> echo preg_match('(\bdart\b|\bfart\b)', $gun4);
0

所以和前面的例子一样,只是内容中不存在fart带词边界的词: .\bfarty

于 2014-01-06T17:51:24.340 回答
8

使用\b可以产生令人惊讶的结果。您最好弄清楚单词与其定义的区别并将该信息合并到您的模式中。

#!/usr/bin/perl

use strict; use warnings;

use re 'debug';

my $str = 'S.P.E.C.T.R.E. (Special Executive for Counter-intelligence,
Terrorism, Revenge and Extortion) is a fictional global terrorist
organisation';

my $word = 'S.P.E.C.T.R.E.';

if ( $str =~ /\b(\Q$word\E)\b/ ) {
    print $1, "\n";
}

输出:

编译 REx "\b(S\.P\.E\.C\.T\.R\.E\.)\b"
最终程序:
   1:绑定 (2)
   2:打开 1 (4)
   4:准确(9)
   9:关闭 1 (11)
  11:绑定 (12)
  12:结束(0)
在 0 锚定“SPECTRE”(检查锚定) stclass BOUND minlen 14
在 sv 中猜测 REx "\b(S\.P\.E\.C\.T\.R\.E\.)\b" 对 "SP" 的匹配开始
.ECTRE(反情报特别执行官,...
在偏移量 0 处找到锚定 substr“SPECTRE”...
start_shift: 0 check_at: 0 s: 0 endpos: 1
与STCLASS不矛盾...
猜测:在偏移量 0 处匹配
将 REx "\b(S\.P\.E\.C\.T\.R\.E\.)\b" 与 "SPECTRE (Special Exec
反情报用途,“...
   0 | 1:绑定(2)
   0 | 2:打开1(4)
   0 | 4:精确 (9)
  14 | 9:关闭1(11)
  14 | 11:绑定(12)
                                  失败的...
匹配失败
释放 REx: "\b(S\.P\.E\.C\.T\.R\.E\.)\b"
于 2009-11-17T20:03:41.263 回答
2

如果您在 Notepad++ 中执行此操作

[\w]+ 

会给你整个单词,你可以添加括号将它作为一个组来获取。示例:conv1 = Conv2D(64, (3, 3), activation=LeakyReLU(alpha=a), padding='valid', kernel_initializer='he_normal')(inputs)。我想LeakyReLU作为评论移入它自己的行,并替换当前的激活。在记事本++中,这可以使用以下查找命令来完成:

([\w]+)( = .+)(LeakyReLU.alpha=a.)(.+)

并且替换命令变为:

\1\2'relu'\4 \n    # \1 = LeakyReLU\(alpha=a\)\(\1\)

空格是为了在我的代码中保持正确的格式。:)

于 2019-06-11T10:55:14.790 回答
2

对于那些想要在他们的代码中验证枚举的人,您可以按照指南进行操作

在 Regex World 中,您可以使用开始和结束^字符串。$结合使用它们|可能是您想要的:

^(Male)$|^(Female)$

它只会返回 true for Maleor Femalecase。

于 2020-08-05T10:20:42.173 回答
1

使用单词边界\b,

以下(使用四个转义)适用于我的环境:Mac,safari 版本 10.0.3 (12602.4.8)

var myReg = new RegExp(‘\\\\b’+ variable + ‘\\\\b’, ‘g’)
于 2018-06-07T18:11:56.463 回答
-1

获取字符串中的所有“单词”

/([^\s]+)/g

基本上^/s意味着打破空格(或匹配非空格组)
不要忘记gfor Greedy

于 2020-03-17T21:14:21.903 回答