Reputation:
Let's say I have this dataset
> example <- data.frame(a = 1:10, b = 10:1, c = 1:5 )
I want to create a new variable d
. I want in d
the value 1 when at least in of the variables a b c
the value 1 2 or 3 is present.
d
should look like this:
d <- c(1, 1, 1, 0, 0, 1, 1, 1, 1, 1)
Thanks in advance.
Upvotes: 2
Views: 1958
Reputation: 11128
You can do this using apply(although little slow)
Logic: any
will compare if there is any 1,2 or 3 is present or not, apply
is used to iterate this logic on each of the rows. Then finally converting the boolean outcome to numeric by adding +0 (You may choose as.numeric
here in case you want to be more expressive)
d <- apply(example,1 ,function(x)any(x==1|x==2|x==3))+0
In case someone wants to restrict the columns or want to run the logic on some columns, then one can do this also:
d <- apply(example[,c("a","b","c")], 1, function(x)any(x==1|x==2|x==3))+0
Here you have control on columns on which one to take or ignore basis your needs.
Output:
> d
[1] 1 1 1 0 0 1 1 1 1 1
Upvotes: 1
Reputation: 83215
Two other possibilities which work with any number of columns:
#option 1
example$d <- +(rowSums(sapply(example, `%in%`, 1:3)) > 0)
#option 2
library(matrixStats)
example$d <- rowMaxs(+(sapply(example, `%in%`, 1:3)))
which both give:
> example a b c d 1 1 10 1 1 2 2 9 2 1 3 3 8 3 1 4 4 7 4 0 5 5 6 5 0 6 6 5 1 1 7 7 4 2 1 8 8 3 3 1 9 9 2 4 1 10 10 1 5 1
Upvotes: 1
Reputation: 11480
general solution:
example %>%
sapply(function(i)i %in% x) %>% apply(1,any) %>% as.integer
#[1] 1 1 1 0 0 1 1 1 1 1
Upvotes: 0
Reputation: 3619
With the dplyr
package:
library(dplyr)
x <- 1:3
example %>% mutate(d = as.integer(a %in% x | b %in% x | c %in% x))
Upvotes: 1
Reputation: 5456
Will work for any number of vars:
example <- data.frame(a = 1:10, b = 10:1, c = 1:5 )
x <- c(1, 2, 3)
as.integer(Reduce(function(a, b) (a %in% x) | (b %in% x), example))
Upvotes: 1
Reputation: 5017
Try this method, verify if in any column there is at list one element present in x
.
x<-c(1,2,3)
example$d<-as.numeric(example$a %in% x | example$b %in% x | example$c %in% x)
example
a b c d
1 1 10 1 1
2 2 9 2 1
3 3 8 3 1
4 4 7 4 0
5 5 6 5 0
6 6 5 1 1
7 7 4 2 1
8 8 3 3 1
9 9 2 4 1
10 10 1 5 1
Upvotes: -1
Reputation: 51582
You can use rowSums
to get a logical vector of 1, 2 or 3
appearing in each row and wrap it in as.integer
to convert to 0 and 1, i.e.
as.integer(rowSums(df == 1|df == 2| df == 3) > 0)
#[1] 1 1 1 0 0 1 1 1 1 1
Upvotes: 2