¿Hay alguna forma de extraer números de las cadenas que aparecen al final?

asd <- c("asdf sfsfsd54 sdfsdfsdf sdfsdfsf654")
asd1 <- c("asdf sfsfsd54 sdfsdfsdf sdfsdfsf65421")

Producción esperada

new_asd 
654

new_asd1
65421
r
2
manu p 11 ene. 2022 a las 13:32
¿Responde esto a tu pregunta? Extracción de números de vectores de cadenas
 – 
Maël
11 ene. 2022 a las 13:37
No No. El caso es que solo hay que extraer los números que aparecen al final
 – 
manu p
11 ene. 2022 a las 13:38
¿Hay cadenas que no terminan en un número? Si es así, ¿cómo espera manejarlos? ¿Quiere devolver NA o devolver el número más cercano al final? Si es lo primero, entonces la expresión regular necesitará $ en ella. Muchas de las respuestas a continuación le darán el último resultado.
 – 
Michael Dewar
11 ene. 2022 a las 15:26

7 respuestas

Este código extrae siempre las últimas entradas numéricas de una cadena:

(stringr::str_extract(asd, stringr::regex("(\\d+)(?!.*\\d)")))
"654"
(stringr::str_extract(asd1, stringr::regex("(\\d+)(?!.*\\d)")))
"65421"

Si desea obtener solo el número cuando el último carácter de la cadena es un número, puede implementar una condición ifelse simple para verificar eso específicamente, por ejemplo:

x<- c("asdf sfsfsd54 sdfsdfsdf sdfsdfsf654f")
ifelse(!is.na(as.numeric(substr(x, nchar(x), nchar(x)))), 
       (stringr::str_extract(x, stringr::regex("(\\d+)(?!.*\\d)"))),
       NA)
NA #returns NA because last entry of string is not numeric ("f")
3
JKupzig 11 ene. 2022 a las 17:07
Su expresión regular extrae incorrectamente "1" de "a1a".
 – 
Michael Dewar
11 ene. 2022 a las 14:13
Agregué una condición ifelse para dar cuenta de eso como una extensión de mi código. Gracias por el comentario.
 – 
JKupzig
11 ene. 2022 a las 17:16

Una solución que primero divide la cadena en función de los espacios en blanco, luego obtiene la última subcadena y elimina las letras. Esto debería funcionar siempre que solo haya letras y números en las cadenas.

library(stringr)

get_num = function(x) {
    str_remove_all(rev(unlist(str_split(x, " ")))[1], "[a-z]")
}
> get_num(asd)
[1] "654"
> get_num(asd1)
[1] "65421"
1
user438383 11 ene. 2022 a las 13:51

Si la cadena siempre termina con dígitos, entonces podemos probar gsub

> x <- c("asdf sfsfsd54 sdfsdfsdf sdfsdfsf654", "asdf sfsfsd54 sdfsdfsdf sdfsdfsf65421")

> gsub(".*\\D", "", x, perl = TRUE)
[1] "654"   "65421"
1
ThomasIsCoding 11 ene. 2022 a las 13:56

Una sola expresión regular es suficiente para su situación.

stringr::str_extract(asd, "(\\d+$)")

$ ancla el grupo de captura al final de la cadena.

1
Michael Dewar 11 ene. 2022 a las 14:15

También podemos usar stri_extract_last_regex de stringi

> library(stringi)
> stri_extract_last_regex(asd, "\\d+")
[1] "654"
> stri_extract_last_regex(asd1, "\\d+")
[1] "65421"
1
akrun 11 ene. 2022 a las 20:14

Usaría sub combinado con ifelse aquí:

x <- c("asdf sfsfsd54 sdfsdfsdf sdfsdfsf654", "abc", "123")
nums <- ifelse(grepl("\\d$", x), sub(".*?(\\d+)$", "\\1", x), "")
nums

[1] "654" ""    "123"
1
Tim Biegeleisen 11 ene. 2022 a las 13:43

Puedes hacer algo como esto:

library(stringr)
val <- str_extract_all(asd1, "\\d+")[[1]]
tail(val, 1)
"65421"

O

as.numeric(gsub("[^\\d]+", "", asd, perl=TRUE))
val <- regmatches(asd1, gregexpr("[[:digit:]]+", asd1))[[1]]
tail(val, 1)
"65421"
0
Vishal A. 11 ene. 2022 a las 13:49