R sub/gsub 替换第一次出现的匹配项

R sub/gsub replacing first occurence of match

在 R 中,我需要从以下字符串中提取 "Eight":

this_str <- " Eight years blah blah 50 blah blah, two years blah blah blah."

这是我使用 gsub 的尝试:

gsub("^.*\s([^ ]*)\s(years|months)\s.*", "\1", this_str)

但是这个returns "two",它对应于gsub()中指示的模式的第二次出现。在其他帖子中,据说 sub() 应该 return 第一场比赛。但是当我使用 sub() 它也会给出 "two".

sub 进行一次替换,而 gsub 进行多次替换。相反,问题是开头的 .*greedy:它上升到 "two"(即,包括除最后一场比赛以外的所有比赛)。相反,我们想要 lazy(参见 here)并尽可能少地匹配:

sub("^.*?\s([^ ]*)\s(years|months)\s.*", "\1", this_str)
# [1] "Eight"

这里,我们很可能会使用一个表达式来传递可选空格,以防万一,例如:

(\s+)?(.+?)(\s+)?(years?|months?).*

我们想要的输出在第二个捕获组中:

(.+?)

我们的代码看起来像

gsub("(\s+)?(.+?)(\s+)?(years?|months?).*", "\2", this_str)

Demo

正则表达式

如果不需要此表达式并且您希望修改它,请访问 link regex101.com

正则表达式电路

jex.im 可视化正则表达式: