Search code examples
rif-statementdplyrany

Using any in nested ifelse statement


data:

set.seed(1337)
m <- matrix(sample(c(0,0,0,1),size = 50,replace=T),ncol=5) %>% as.data.frame
colnames(m)<-LETTERS[1:5]

code:

m %<>%
        mutate(newcol       = ifelse(A==1&(B==1|C==1)&(D==1|E==1),1,
                                     ifelse(any(A,B,C,D,E),0,NA)),
               desiredResult= ifelse(A==1&(B==1|C==1)&(D==1|E==1),1,
                                     ifelse(!(A==0&B==0&C==0&D==0&E==0),0,NA)))

looks like:

   A B C D E newcol desiredResult
1  0 1 1 1 0      0             0
2  0 1 0 0 1      0             0
3  0 1 0 0 0      0             0
4  0 0 0 0 0      0            NA
5  0 1 0 1 0      0             0
6  0 0 1 0 0      0             0
7  1 1 1 1 0      1             1
8  0 1 1 0 0      0             0
9  0 0 0 0 0      0            NA
10 0 0 1 0 0      0             0

question

I want newcol to be the same as desiredResult.

Why can't I use any in that "stratified" manner of ifelse. Is there a function like any that would work in that situation?

possible workaround

I could define a function any_vec <- function(...) {apply(cbind(...),1,any)} but this does not make me smile too much.

like suggested in the answer

using pmax works exactly like a vectorized any.

m %>%
    mutate(pmaxResult = ifelse(A==1& pmax(B,C) & pmax(D,E),1,
                                 ifelse(pmax(A,B,C,D,E),0,NA)),
           desiredResult= ifelse(A==1&(B==1|C==1)&(D==1|E==1),1,
                                 ifelse(!(A==0&B==0&C==0&D==0&E==0),0,NA)))

Solution

  • Here's an alternative approach. I converted to logical at the beginning and back to integer at the end:

    m %>% 
      mutate_all(as.logical) %>% 
      mutate(newcol       = A & pmax(B,C) & pmax(D, E) ,
             newcol       = replace(newcol, !newcol & !pmax(A,B,C,D,E), NA)) %>% 
      mutate_all(as.integer)
    
    #    A B C D E newcol
    # 1  0 1 1 1 0      0
    # 2  0 1 0 0 1      0
    # 3  0 1 0 0 0      0
    # 4  0 0 0 0 0     NA
    # 5  0 1 0 1 0      0
    # 6  0 0 1 0 0      0
    # 7  1 1 1 1 0      1
    # 8  0 1 1 0 0      0
    # 9  0 0 0 0 0     NA
    # 10 0 0 1 0 0      0
    

    I basically replaced the any with pmax.