我有一个正则表达式,用于捕获数字符号后面的关键字:
/^#\s*([a-zA-Z\-\s]+)/
但是,我需要更改正则表达式以指定不匹配包含星号的字符串。例如,我需要正则表达式匹配# keyword
,但不是 # *keyword
。
以下是我解决此问题的最佳尝试:
/^#\s[^[*]]*([a-zA-Z\-\s]+)/
我是Perl的新手,所以我确信解决方案非常简单,但我花在研究和试错上的时间并没有给我带来太多帮助。
答案 0 :(得分:3)
假设我理解正确,你的第一个正则表达式就好了。由于它是白名单并且星号不在其中,因此它与包含星号字符的关键字不匹配:
/^#\s*([a-zA-Z\-\s]+)/
这仍然匹配:
# key*word
...虽然只会匹配key
。一种解决方案,如果您确定只有关键字将占用该行的其余部分,则只会强制列入白名单的字符直到该行的结尾,如下所示:
/^#\s*([a-zA-Z\-\s]+)$/
这是另一种选择。如果您只想确保初始哈希和空格之后的第一组字符不包含星号,则可以使用:
/^#\s*([a-zA-Z\-]+)(?:\s|$)/
这将匹配:
# keyword foo
它会匹配:
# keyword
但它不匹配:
# key*word foo
也:
# key*word
也:
# key* word foo
Nor:
# **** keyword
答案 1 :(得分:1)
我认为问题在于你是否部分匹配带星号的字符串,如下所示:
foobar* => matching string "foobar"
你可能会尝试使用负面前瞻断言,如下所示:
/^#\s*(?!.*\*)(.+)/
这个.*\*
声称没有星号出现在英镑符号前面的任何地方。然而,这只是一种在一个方面做两件事的奇特方式:
if (!/\*/ && /^#\s*(.+)/) { ...
答案 2 :(得分:1)
尝试使用此正则表达式进行匹配:
^#\s*([-a-zA-Z]+)(?=\s|$)
你的正则表达式已经与# *keyword
不匹配,但是这个正则表达式从捕获的组中删除了空格并使用前瞻来断言该单词后面的字符不是星号,因此它不匹配# key*word
。
另请注意,当它是字符类中的第一个(或最后一个)字符时,不必转义破折号的这种轻微简化。
在rubular上查看此live demo。