r-如何查找字符串中的最后一组数字



假设我有一个字符串

"Happy 2022 New 01 years!"

我想把";01";。更具体地说,我需要字符串中的最后一组数字。这个数字可能只是"1"、"10"或"999"。。。否则,绳子几乎可以是任何东西。我用gsub尝试了各种正则表达式,但似乎都做不好。有件事我误解了。

例如,如果我这样做:

gsub('.*(\d+).*$', '\1', x)

那我为什么要回来;1〃;?正则表达式中的"+"是否未指定一个或多个数字?

我的解释怎么错了?:">'表示任何字符,'(\\d+('表示一个或多个数字,''对于更多的字符,在字符串末尾添加'$'。gsub是贪婪的,所以它将返回最后一组数字(因此是"01",而不是"2022"(\\1'将用第一个也是唯一一个匹配项替换整个字符串。x是字符串。

在正则表达式中,.*将匹配所有字符(换行符除外(,从而匹配整个字符串。然后,引擎尝试匹配d+,但字符串中已没有要匹配的字符。因此,在.*中进行反向跟踪,直到找到一个数字。一旦找到一个数字(即,在您的情况下为1(,d+将与该数字匹配,字符串的其余部分将再次由.*匹配。

你可以试试这个正则表达式:

d+(?![^rnd]*d)

点击演示

解释:

  • d+-匹配1个或多个数字,尽可能多
  • (?![^rnd]*d)-负前瞻,以确保字符串后面不再有数字

在目标最终数字周围放置单词边界:

x <- "Happy 2022 New 01 years!"
num <- gsub('.*\b(\d+)\b.*$', '\1', x)
num
[1] "01"

这里的挑战是,我们很想使用一个懒惰的点来停止在第一个数字,例如.*?(\d+).*。但问题是,现在我们将停留在第一个数字,尽管我们想要最后一个。因此,贪婪点是合适的,单词边界迫使正则表达式捕获整个最终数字。

这可以工作:

(d+)[^d]*$

https://regex101.com/r/DHrttA/1

在你的解决方案中,我认为问题是第一个.*是贪婪的,所以它会跳过它所能跳过的。

使用strsplit的解决方法

> tail(strsplit(x, "\D+")[[1]], 1)
[1] "01"