Search code examples
rloopsif-statementsample

R looping through vector with ifelse


I want ifelse to loop through and vector and if condition is true (value = either 2 or 3) I want to sample a set, if not set the value to zero. This code works but it appears to only do the sampling once, and the same value is recycled. Is it possible to get it execute the sampling for each value of the array?

vec1 <- sample(1:7, 5, replace = TRUE)

vec2 <- ifelse (vec1 == 2 | vec1 == 3,
                sample(0:3, 1),
                0
                )
vec2
[1] 3 3 0 0 3

It works but I was hoping for different values in vec2 positions 1,2 and 5, not all the same value which happens every time. So I would hope to see random sampling, and end up with

vec2 [1] 1 3 0 0 3

or

vec2 [1] 1 2 0 0 3

Something missing in my logic and/or code. Thx, J


Solution

  • Your sample(0:3, 1) is "recycled" just like your 0... it's not re-run every time it's needed. You need to pre-generate all the replacements so they can be used if needed. Do this:

    ifelse(vec1 %in% c(2, 3), sample(0:3, size = length(vec1), replace = TRUE), 0)
    

    I also like vec1 %in% c(2, 3) more than vec1 == 2 | vec1 == 3 because it scales up better... if you had more than 2 possibilities, %in% is easy to add to, but == | == | == gets old quickly.

    Alternately, if you care about speed/efficiency, this will be quicker:

    to_replace = which(vec1 %in% c(2, 3))
    vec1[to_replace] = sample(0:3, size = length(to_replace), replace = TRUE)