EmKayDee
EmKayDee

Reputation: 183

ifelse statements for multiple combinations of conditions

I often run into cases where I want to write ifelse statements that contain multiple combinations of conditions, and I end up just writing out every possible combination that fits my criteria. I'm sure there must be a more efficient way of doing this.

observation <- c(1:3, 1:3, 1:3, 1:3)
var1 <- c(0, 0.3, 0.3, 5, -0.3, -0.6, -4, 6,-0.75, 0.75, 3, 0.75)
dat <- as.data.frame(cbind(observation, var1))

In this example, I'm interested in creating a flag for extreme values (that is, values that are greater than 1 or less than -1) that occur during the second observation.

I'm hoping there is some way of asking R to do something like create a flag if observation == 2 and EITHER var1 > 1 OR var1 < -1, make it 1, otherwise make it 0

But the best I know to do is write separate nested ifelse statements, like

dat$flag <- with(dat, ifelse(observation == 2 & var1 > 1, 1, 
ifelse(observation == 2 & var1 < -1, 1, 0)))

Obviously this isn't terrible in the example case, but I often have a lot of combination conditions--like I want to flag all records for students who were in 9th-12th grade during 2014-2018, which means also flagging records for students who were in 9th-11th grade in 2013 and who were in 9th-10th grade in 2012 and who were in 9th grade in 2011. But hopefully that example gets the picture across :) Thanks for your help!

Upvotes: 1

Views: 906

Answers (2)

DJV
DJV

Reputation: 4863

As mentioned by @RonakShah you can avoid ifelse() or use it without nesting. However, in cases where you do need nested ifelse() you can just use dplyr::case_when():

require(tidyverse)

dat %>% 
  mutate(flag1WithIfelse = ifelse(observation == 2 & (var1 > 1 |var1 < -1), 
                                  1, 0), 
         flag2WithCaseWhen = case_when(
           observation == 2 & (var1 > 1 |var1 < -1) ~ 1, 
           TRUE ~ 0))


   observation  var1 flag1WithIfelse flag2WithCaseWhen
1            1  0.00               0                 0
2            2  0.30               0                 0
3            3  0.30               0                 0
4            1  5.00               0                 0
5            2 -0.30               0                 0
6            3 -0.60               0                 0
7            1 -4.00               0                 0
8            2  6.00               1                 1
9            3 -0.75               0                 0
10           1  0.75               0                 0
11           2  3.00               1                 1
12           3  0.75               0                 0

Upvotes: 1

Ronak Shah
Ronak Shah

Reputation: 389012

In this case you would not even need ifelse. You could combine two conditions by

+with(dat, observation == 2 & (var1 > 1 | var1 < -1))
#[1] 0 0 0 0 0 0 0 1 0 0 1 0

With ifelse you could use like

dat$flag <- with(dat, ifelse(observation == 2 & (var1 > 1 |var1 < -1), 1, 0))

#   observation  var1 flag
#1            1  0.00    0
#2            2  0.30    0
#3            3  0.30    0
#4            1  5.00    0
#5            2 -0.30    0
#6            3 -0.60    0
#7            1 -4.00    0
#8            2  6.00    1
#9            3 -0.75    0
#10           1  0.75    0
#11           2  3.00    1
#12           3  0.75    0

Upvotes: 2

Related Questions