Regex:匹配带下划线的单词,除非它们以@/#开头



我正试图通过传递自定义正则表达式来解决Tiptap(Vue的所见即所得编辑器(中的这个错误,以便在Markdown(_value_(中标识斜体符号的正则表达式不会应用于以@#开头的字符串,例如#some_tag_value不会转换为#some标记值。

这是我迄今为止的正则表达式-/(^|[^@#_w])(?:w?)(_([^_]+)_)/g
编辑:在@Wiktor Stribiżew/(^|[^@#_w])(_([^_]+)_)/g的帮助下创建新正则表达式

虽然它满足了大多数常见情况,但当下划线是中间词,例如ant_farm_应该匹配(antfarm(

我还在这里提供了一些"应该匹配"one_answers"不应该匹配"的情况https://regexr.com/50ibf更容易测试

应匹配(下划线之间(

_italic text here_
police_woman_
_fire_fighter
a thousand _words_
_brunch_ on a Sunday

不应匹配

@ta_g_
__value__
#some_tag_value
@some_value_here
@some_tag_
#some_val_
#_hello_

您可以使用以下模式:

(?:^|s)[^@#s_]*(_([^_]+)_)

查看regex演示

详细信息

  • (?:^|s)-字符串或空白的开头
  • [^@#s_]*-除@#_和空白之外的0个或更多字符
  • (_([^_]+)_)-第1组:_,除_之外的1+个字符(捕获到第2组(,然后是_

对于科学来说,这个怪物可以在Chrome(和Node.js(中工作

let text = `
<strong>Should match</strong> (between underscores)
_italic text here_
police_woman_
_fire_fighter
a thousand _words_
_brunch_ on a Sunday
<strong>Should not match</strong>
@ta_g_
__value__
#some_tag_value
@some_value_here
@some_tag_
#some_val_
#_hello_
`;
let re = /(?<=(?:s|^)(?![@#])[^_n]*)_([^_]+)_/g;
document.querySelector('div').innerHTML = text.replace(re, '<em>$1</em>');
div { white-space: pre; }
<div/>

这将_something_捕获为完全匹配,并将something捕获为第一个捕获组(以便删除下划线(。你不能只捕获something,因为那样你就失去了区分下划线内部和外部的能力(用(?<=(?:s|^)(?![@#])[^_n]*_)([^_]+)(?=_)试试(。

有两件事阻碍了它的普遍适用:

  • 并非所有JavaScript引擎都支持Look behinds
  • 大多数regexp引擎不支持可变长度的look behinds

EDIT:这有点强,应该允许您正确地添加match_this_and_that_ but not @match_this_and_that

/(?<=(?:s|^)(?![@#])(?!__)S*)_([^_]+)_/

说明:

_([^_]+)_    Match non-underscory bit between two underscores
(?<=...)     that is preceded by
(?:s|^)     either a whitespace or a start of a line/string
(i.e. a proper word boundary, since we can't use `b`)
S*          and then some non-space characters
(?![@#])     that don't start with `@`, `#`,
(?!__)       or `__`.

regex101演示

这里有一些东西,它不像其他答案那样紧凑,但我认为它更容易理解发生了什么。匹配组3就是你想要的。

需要多行标志

^([a-zA-Zs]+|_)(([a-zA-Zs]+)_)+?[a-zA-Zs]*?$
  • ^-匹配行的开头
  • ([a-zA-Zs]+|_)-多个单词或_
  • (([a-zA-Zs]+)_)+?-多个单词后面跟着_至少一次,但最小匹配
  • [a-zA-Zs]*?-任何最终单词
  • $-线路末端

总之,与匹配的事物的分解

  • _<words>_
  • <words>_<words>_
  • <words>_<words>_<words>
  • _<words>_<words>

相关内容

最新更新