正则表达式匹配一个单词,但不匹配反引号

时间:2020-10-27 18:47:14

标签: javascript regex

以下是不同段落的示例

Upgrade is the first word in this paragraph.
In this paragraph, upgrade is the last word.
And this paragraph endsupgrade with upgrade.
But I don't want to upgradefind that word in this command `gigalixir:upgrade`.

您可以看到上述四行中有6个升级单词实例。我正在尝试查找除最后一个以外的所有升级词(因为该词位于反引号内的命令内)。我也不想找到不是独立的升级词。

因此在以上句子中,应选择带有双*的单词:

**Upgrade** is the first word in this paragraph.
In this paragraph, **upgrade** is the last word.
And this paragraph endsupgrade with **upgrade**.
But I don't want to upgradefind that word in this command `gigalixir:upgrade`.

我已经尝试过这个简单的正则表达式:

/\bupgrade\b/gi

这会选择所有独立的单词,但我想忽略反引号内的升级单词。

注意:我不想使用先行或后退方式,因为我是在浏览器中执行此正则表达式的,而除chrome之外的任何浏览器均不支持此正则表达式。

1 个答案:

答案 0 :(得分:1)

您可以在反引号内匹配字符串并跳过它们,仅在所有其他上下文中将一个单词upgrade匹配为一个整体单词:

const text = 'Upgrade is the first word in this paragraph.\nIn this paragraph, upgrade is the last word.\nAnd this paragraph endsupgrade with upgrade.\nBut I don\'t want to upgradefind that word in this command `gigalixir:upgrade`.';
const regex = /(`[^`]*`)|\bupgrade\b/gi;
console.log(text.replace(regex, (x,y) => y || `**${x}**`));

(`[^`]*`)|\bupgrade\b正则表达式匹配

  • (`[^`]*`)-捕获组1(稍后将帮助分析匹配结构):反引号,除反引号以外的零个或多个字符和一个反引号
  • |-或
  • \bupgrade\b-整个单词upgrade(由于带有i标志,因此不区分大小写)。

.replace(regex, (x,y) => y || `**${x}**`)意味着找到匹配项后,该匹配项将传递到箭头函数,其中x是整个匹配项,而y是第1组值。如果第1组的值匹配,则使用其值替换匹配项,否则,整个匹配项将包含双星号。

或者,您可以使用已知的变通方法,并使用负前瞻,仅在字符串中有成对的反引号时才有效:

\bupgrade\b(?=(?:[^`]*`[^`]*`)*[^`]*$)

请参见regex demo

(?=(?:[^`]*`[^`]*`)*[^`]*$)前瞻匹配的位置紧随其后是

  • (?:[^`]*`[^`]*`)*对除反引号以外的任何零个或多个字符进行零次或更多次重复,然后加上反引号,然后再次选择除反引号外的任意零个或多个字符,然后再次反引号
  • [^`]*-除反引号外的任何零个或多个字符
  • $-字符串的结尾。