gpt4 book ai didi

用正则表达式替换时,Ruby gsub 不遵守命名组

转载 作者:数据小太阳 更新时间:2023-10-29 08:52:19 24 4
gpt4 key购买 nike

我需要用引号子字符串中未出现的逗号分隔字符串。我的做法是

  • 用一些特殊标记替换带引号的子字符串中的逗号,
  • 用逗号分隔字符串,然后
  • 用逗号替换出现的标记(在拆分的字符串中)。

我意识到可能有一种更简单的方法可以做到这一点,但现在我只想知道为什么命名组替换不起作用,如下所述。

我有一个正则表达式,将带引号的子字符串中的逗号标识为命名捕获 commahere:

COMMA_INSIDE_QUOTES_REGEX = /
(?<quote>[\"\']) # start by finding either single or double quote
(?<postquote>.*?) # then lazy capture any other chars until...
(?<commahere>\,) # ...we find the comma
(?<postcomma>.*?) # then lazy capture any other chars until...
(\k<quote>) # ...we find the matching single or double quote
/x

在下面的测试字符串中,正则表达式匹配 de,fjk,a,l 但不匹配其他字符串,如我所料。

str = 'abc,"de,f",ghi,"jk,a,l"'
COMMA_INSIDE_QUOTES_REGEX.match(str)
#=> #<MatchData "\"de,f\"" quote:"\"" postquote:"de" commahere:"," postcomma:"f">

但是当我使用 gsub 将命名捕获替换为特殊标记时,整个匹配被替换,而不是命名组(再加上两个逗号!):

COMMA_TOKEN = '<--COMMA-->'
str.gsub(COMMA_INSIDE_QUOTES_REGEX,"\\k<commahere>#{COMMA_TOKEN}")
#=> "abc,,<--COMMA-->,ghi,,<--COMMA-->"

最佳答案

你误会了什么。

str.gsub(COMMA_INSIDE_QUOTES_REGEX,"\\k<commahere>#{COMMA_TOKEN}")

意思是:

  1. 尝试匹配正则表达式 COMMA_INSIDE_QUOTES_REGEX在字符串 str 中.
  2. 如果成功,将整个匹配项替换为根据<commahere> 的内容构建的字符串和COMMA_TOKEN的内容.

这并不意味着“仅用它后面的任何内容替换组 <commahere>。您的方法是错误的,并且您尝试做的事情不能按照您尝试做的方式完成。您应该确实采纳了 mu 的建议并使用 CSV 解析器。

如果您对实际可行的正则表达式感兴趣,则必须像这样构建它:

  1. 匹配一个逗号。
  2. 检查这个逗号是否在字符串中。这可以通过计算逗号后面的引号数来完成。如果该数字是奇数,则逗号位于字符串内。
  3. 即使引号嵌入在字符串本身中,之前的技巧也能奏效,因为这些引号通过加倍转义。

所以,这是你的正则表达式:

result = str.gsub(
/, # Match a comma
(?! # only if it's not followed by
(?: # the following group:
[^"]*" # any number of non-quote characters and a quote
[^"]*" # twice (so exactly two quotes are matched)
)* # any number of times (including 0)
[^"]* # followed (if at all) by only non-quote characters
\Z # until the end of the string.
) # End of lookahead
/x, '<--COMMA-->')

关于用正则表达式替换时,Ruby gsub 不遵守命名组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9761418/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com