【问题标题】:Need regex to match first occurence of a character in a string需要正则表达式来匹配字符串中第一次出现的字符
【发布时间】:2018-02-22 05:39:06
【问题描述】:

我有一个 sql 查询作为字符串,我需要一个正则表达式来匹配字符串中的第一个问号 (?)

select * from something where a = ? and b=? and c=?

正则表达式应该只匹配第一次出现的问号。我将在 Neo4j-apoc 库 (apoc.text.replace function) 中使用这个正则表达式。与 Perl/Java 等不同,此库不提供任何标志或 api 来获得第一个匹配项。所以我必须完全依靠正则表达式来匹配第一个字符。

我尝试了以下一些正则表达式,但没有运气

这些正则表达式不匹配

(?<=^[^?]{0,1000})[?]

这些正则表达式匹配所有不存在的字符和所有问号

[?]?
([?])?
([\?])?
([\?])??
([?])*?

这些正则表达式匹配所有问号

([?])+?
[?]+?

有人可以帮我写这个正则表达式吗?

【问题讨论】:

  • 总是有3个问号吗?如果没有,将第一个 ? 捕获为第 1 组的正则表达式是否有效?
  • 你的意思是this
  • @Bohemian,上面的查询只是一个示例,可以没有问号,也可以有 n 个问号。我只需要匹配第一个。我不能在 neo4j-apoc 库中使用组。我需要一个只匹配第一个的正则表达式?。

标签: regex regex-lookarounds regex-group neo4j-apoc


【解决方案1】:

我想出了一个奇怪的解决方案,但也许你会接受这个:
(?&lt;!\?)\?{1}(?!.*?\?)|(?&lt;=\?)\?{1}(?!.*?\?)
将仅匹配 last ?
因此,虽然您无法直接找出第一个,但您可以反转您的字符串,然后找到最后一个。
我用Regex101 来测试它。

[更新]:
它会在\n 之前找到?最后 次出现。

【讨论】:

  • 看起来很有帮助,我试试看能不能用这个。谢谢
  • @Fayaz 不客气。谢谢你的问题,思考这个问题很有趣。
【解决方案2】:

你可以使用([^?]+)(\?)(.+)

你可以用$2得到第一个问号

Online demo

【讨论】:

  • 这个正则表达式匹配整个字符串和第一个问号。当我在 neo4j-apoc(apoc.text.replace 函数)中使用它时,它将替换整个字符串。我只需要匹配第一个问号而不是字符串的其他部分。
【解决方案3】:

您不能将 lookbehind(?&lt;=^[^?]{0,1000}) 之类的量词一起使用。

在这种情况下(至少在 regex101.com 中),您会收到一条错误消息: {0,1000} A quantifier inside a lookbehind makes it non-fixed width.

要匹配第一个 ?,你可以使用^[^?]*(\?),意思是:

  • ^ - 字符串的开头。
  • [^?]* - ? 以外的字符序列(可能为空)。
  • (\?) - 您要捕获的字符。

第一个? 将是第一个捕获组的内容。

编辑

另一种解决方案,如果您使用 PCRE 版本的正则表达式:

^[^?]*\K\?

意思:

  • ^[^?]* - 匹配除? 之外的“初始”字符序列。
  • \K - “忘记”到目前为止匹配的内容,从这里开始匹配。
  • \? - 匹配 ?

这样你的整个匹配是第一个?,没有任何捕获组。

【讨论】:

    【解决方案4】:

    如果您的正则表达式引擎支持positive lookbehind(?&lt;,请仅选择您可以使用的第一个问号:

    (?&lt;=where a = )\? 或不带 where (?&lt;=a = )\?

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-01-02
      • 1970-01-01
      • 2011-09-22
      • 2013-07-26
      • 2016-09-28
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多