1

I have a data.frame, where one column is a list (see this post) I would like to check which lists within the data.frame contain an element (let's say the number 3) Currently, I am looping through all rows of the data.frame.

df=data.frame(a=1:3,b=I(list(1,3:7,1:3)))
df
for(i in 1:nrow(df)){
     print(3 %in% df$b[[i]])

}

Is there a more elegant way?

Community
  • 1
  • 1
Peter
  • 355
  • 1
  • 8
  • 23
  • 1
    You could use `apply(df, 1, function(x) 3 %in% unlist(x[2]))` which loops also, but perhaps 'elegant.' – Gopala May 19 '16 at 13:24
  • 3
    I would go with ```mapply(`%in%`, 3, df$b)``` or `sapply(df$b, function(x) 3 %in% x)` or something similar – David Arenburg May 19 '16 at 13:24
  • 2
    That surely is more elegant. I had not used `mapply` before. Very nice. – Gopala May 19 '16 at 13:25
  • If you have a working solution but want to know what would've been better, then that's a question for Code Review rather than StackOverflow. – Hack-R May 19 '16 at 13:43

2 Answers2

0

Personally I like using map to solve a problem like this, more information can be found here.

library(purrr)
df %>% transpose() %>% map(2) %>% map((function(x) 3 %in% x))

which gives:

[[1]]
[1] FALSE

[[2]]
[1] TRUE

[[3]]
[1] TRUE

Alternatively, there is also map_lgl which returns a logical array rather than a list.

df %>% transpose() %>% map(2) %>% map_lgl((function(x) 3 %in% x))

which give:

[1] FALSE  TRUE  TRUE
idle_mouse
  • 31
  • 5
-1

Yes, try this:

3 %in% unlist(df$b)

The result:

> 3 %in% unlist(df$b)
[1] TRUE

Unlist(df$b) concatenates all the elements of df$b into a vector.

If you have multiple columns:

> apply(df,2,function(x) 3 %in% unlist(x))
   a    b 
TRUE TRUE 
Anton
  • 1,458
  • 1
  • 14
  • 28
  • 1
    I guess they were looking for a result by row (for column "b"). Your solution only tells if 3 appeared anywehere in a column – talat May 19 '16 at 14:13
  • Yes, they were looking for a result for specifically column "b". I'm aware that the second solution for multiple columns looks for 3 anywhere in the column regardless of whether the column contains a list. He will have to subset the columns first. – Anton May 19 '16 at 17:56