if statement - r: when to use if else loops vs. functions -
need resolve loop issue;
example data:
data2 <- structure(list(a = c(101, 102, 103, 104, 105, 106, 107, 108,109,110), b = c(1,1,1,1,2,2,3,4,4,4), c = c(4, 4, 4, 4, 2, 2, 1, 3,3,3)), .names = c("id", "band", "group_qty"), row.names = c(na, 10l), class = "data.frame")
example desired output:
output <- structure(list(a = c(101, 102, 103, 104, 105, 106, 107, 108, 109, 110), b = c(1,1,1,1,2,2,3,4,4,4), c = c(4,4,4,4,2,2,1,3,3,3), d = c(102,103,104,103,"class b","class b","class a",109,110,109)), .names = c("id", "band", "group_qty","newid"), row.names = c(na, 10l), class = "data.frame")
draft if else statement: note: doesn't work.
data2$newid <- for(i in 1:length(data2$id)) { ifelse(data2$[i,3] == 1, "class a", ifelse(data2[i,3] == 2, "class b", ifelse(data2[i,2] == data2[i+1,2], data2[i+1,1], data2[i-1,1]))) }
question:
how create working loop or function can use dplyr. rules:
if group_qty = 1; output = class a
if group_qty = 2; output = class b
else, check see if band match band of next row.
- if yes, output = next row's id
- if no, output = previous row's id
once reach last row of loop - not have row+1. in case: output = previous row's id.
can resolved using dplyr & mutate. if yes, love have possible answer.
thanks,
we can use data.table
. convert 'data.frame' 'data.table' (setdt(data2)
), grouped 'band', if
number of elements in group greater 1 (.n >1
), use shift
type='lead'
succeeding 'id' each group or else
keep 'id' create 'newid' column. then, based on condition, replace value in 'newid' corresponds 'group_qty' 2 'class b' , 1 'class_a' using ifelse
.
library(data.table) setdt(data2)[, newid:=if(.n>1) shift(id, type='lead', fill = id[.n-1]) else id , = .(band)] data2[, newid:= ifelse(group_qty==2, 'class b', ifelse(group_qty==1, 'class a', newid))] data2 # id band group_qty newid # 1: 101 1 4 102 # 2: 102 1 4 103 # 3: 103 1 4 104 # 4: 104 1 4 103 # 5: 105 2 2 class b # 6: 106 2 2 class b # 7: 107 3 1 class # 8: 108 4 3 109 # 9: 109 4 3 110 #10: 110 4 3 109
we can use similar approach dplyr
library(dplyr) data2 %>% group_by(band) %>% mutate(newid = if(n()==1) id else dplyr::lead(id, default= id[n()-1]), newid= ifelse(group_qty==2, 'class b', ifelse(group_qty==1, 'class a', as.character(newid)))) # id band group_qty newid # (dbl) (dbl) (dbl) (chr) #1 101 1 4 102 #2 102 1 4 103 #3 103 1 4 104 #4 104 1 4 103 #5 105 2 2 class b #6 106 2 2 class b #7 107 3 1 class #8 108 4 3 109 #9 109 4 3 110 #10 110 4 3 109
Comments
Post a Comment