8

I want to extract everything but a pattern and return this concetenated in a string.

I tried to combine str_extract_all together with sapply and cat

x = c("a_1","a_20","a_40","a_30","a_28")
data <- tibble(age = x)


# extracting just the first pattern is easy
data %>% 
  mutate(age_new = str_extract(age,"[^a_]"))
# combining str_extract_all and sapply doesnt work
data %>% 
  mutate(age_new = sapply(str_extract_all(x,"[^a_]"),function(x) cat(x,sep="")))


class(str_extract_all(x,"[^a_]"))
sapply(str_extract_all(x,"[^a_]"),function(x) cat(x,sep=""))

Returns NULL instead of concatenated patterns

Cath
  • 23,906
  • 5
  • 52
  • 86
MatzeKnop
  • 163
  • 1
  • 8

2 Answers2

14

Instead of cat, we can use paste. Also, with tidyverse, can make use of map and str_c (in place of paste - from stringr)

library(tidyverse)
data %>% 
  mutate(age_new = map_chr(str_extract_all(x, "[^a_]+"), ~ str_c(.x, collapse="")))

using `OP's code

data %>%
    mutate(age_new = sapply(str_extract_all(x,"[^a_]"),
               function(x) paste(x,collapse="")))

If the intention is to get the numbers

library(readr)
data %>%
     mutate(age_new = parse_number(x))
akrun
  • 874,273
  • 37
  • 540
  • 662
  • 1
    You could also avoid `map_chr` in your first solution and use: `str_extract_all(x, "[^a_]+", simplify = T)[,1]` – Andrew Jul 16 '19 at 14:43
  • The tidyverse answer seems better than the apply solution because it doesn't treat empty results as results when you concatenate – Nick Jun 03 '21 at 20:27
1

Here is a non tidyverse solution, just using stringr.

apply(str_extract_all(column,regex_command,simplify = TRUE),1,paste,collapse="")

'simplify' = TRUE changed str_extract_all to output a matrix, and apply iterates over the matrix. I got the idea from https://stackoverflow.com/a/4213674/8427463

Example: extract all 'r' in rownames(mtcar) and concatenate as a vector

library(stringr)
apply(str_extract_all(rownames(mtcars),"r",simplify = TRUE),1,paste,collapse="")
jf2017
  • 138
  • 1
  • 7