【问题标题】:Negative Lookahead Invalidated by extra numbers in string负前瞻因字符串中的额外数字而无效
【发布时间】:2018-06-27 03:22:00
【问题描述】:

我正在尝试在 R 中编写一个匹配某个字符串的正则表达式,直到出现 . 为止。我认为否定的前瞻可能是答案,但我得到了一些误报。

所以在下面的 9 项向量中

vec <- c("mcq_q9", "mcq_q10", "mcq_q11", "mcq_q12",   "mcq_q1.factor", "mcq_q2.factor", "mcq_q10.factor", "mcq_q11.factor", "mcq_q12.factor")

grep

grep("mcq_q[0-9]+(?!\\.)", vec, perl = T)

对向量中的前六个元素执行其工作,匹配 "mcq_q11" "mcq_q2.factor"。不幸的是,虽然它确实匹配最后 3 个元素,但当第二个 q 后面有两个数字时。为什么第二个数字会消除我的负面预测?

【问题讨论】:

  • 为什么这个标签是 perl -- 你想要一个 Perl 正则表达式吗? (顺便说一句,这是一个消极的前瞻,而不是“lookbehind”)。
  • 第二个数字消除了负前瞻,因为在第二个数字之前 的位置,模式已经成功,包括前瞻,它只检查在那个位置在两个数字之间(除非与 .* 配对)。 (从技术上讲,引擎回溯,[0-9]+ 放弃了一个数字以使 neg-lookahead 成功)
  • @zdim 我标记 perl 是因为 perl=T 函数中的 perl=T 参数,并且因为我收到一条自动消息,说如果您识别一种语言,正则表达式问题的机会更大。
  • 是的,perl=T 参数允许在 R 中的正则表达式相关函数中使用 perl 样式的正则表达式
  • 我将留下我的(已编辑的)Perl 答案,因为它应该适用于您在 R 中的示例。

标签: r regex pcre


【解决方案1】:

我认为您希望您的否定前瞻首先扫描整个字符串,确保它没有看到“点”:

(?!.*\.)mcq_q[0-9]+

https://regex101.com/r/f5XxR2/2/

【讨论】:

  • 这非常聪明@sweaver2112。我对正则表达式了解不多,但我从未见过以这种方式在比赛前进行前瞻。
  • mcq_q[0-9]+(?!.*\.) 在结尾也有效 - 有时将其放在开头会更清楚,在这种情况下可能不是 ;)
【解决方案2】:

如果你要捕捉到一个点,那么你应该使用这个:

mcq_q[0-9]+(?![\d\.])

Demo

示例源 (run here)

vec <- c("mcq_q9", "mcq_q10", "mcq_q11", "mcq_q12",   "mcq_q1.factor", "mcq_q2.factor", "mcq_q10.factor", "mcq_q11.factor", "mcq_q12.factor")
grep("mcq_q[0-9]+(?![\\d\\.])", vec, perl = T)

【讨论】:

  • 谢谢@Rizwan M Tuman,但是将其转变为积极的前瞻,这似乎捕获了我想要排除的元素(即带有.factor 后缀)
  • @llewmills 那么这可能就是你想要的......请查看更新的正则表达式和链接
  • 谢谢@Rizwan M Tuman。我希望我能接受所有的答案,因为它们都很有效并且很巧妙。但是你的被框定为一个负面的前瞻,并且在 grep 中。这些只是次要的事情,但是,由于没有充分的理由来区分一个优秀的答案和另一个,我不得不依靠细节。
【解决方案3】:

我们可以使用它来匹配零个或多个不是. 的字符,在数字 ([0-9]+) 之后直到字符串的末尾 ($)

grep("mcq_q[0-9]+[^.]*$", vec, value = TRUE)
#[1] "mcq_q9"  "mcq_q10" "mcq_q11" "mcq_q12"

【讨论】:

    【解决方案4】:

    正如评论中所解释的那样,负面的前瞻是很棘手的。但你不需要它

    /mcq_q[0-9]+(?:$|[^.0-9])/
    

    这要求一串数字后跟字符串结尾或非 [.,digit] 字符。所以它将允许mcq_q12a 等。如果您允许的字符串只能以数字结尾,请删除|[^...],然后也不需要非捕获组(?:...),因为/mcq_q[0-9]+$/

    仅在 Perl 中测试,因为问题被标记了。您在 R 中的示例应该是相同的。

    【讨论】:

    • “我正在尝试在 R 中编写一个正则表达式,它匹配某个字符串直到出现 . ”并不意味着拥有 .是必须的吗?
    • @RizwanM.Tuman 通过讨论 OP 中的输出,他们显然不想在有点时匹配,所以 没有 点是“必须的” (匹配的术语)。谢谢你的评论,一开始我自欺欺人地认为一个人需要匹配一个可选的点。
    猜你喜欢
    • 2017-03-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-11
    • 2021-06-03
    相关资源
    最近更新 更多