In below variable I want to divide 900000 in below its respective three rows where zero is present, similarly for other values. The number of zeroes to be counted dynamically be
We can use data.table
. We convert the 'data.frame' to data.table' (setDT(df1)
), create a grouping variable ('grp') by checking where 'A_B' is not equal to 0 to create a logical vector and getting the cumulative sum. Grouped by 'grp', we set the 'i' where 'grp' is not equal to 0, create logical vector 'i1' where the 'A_B' is not 0. Get the sum
of 'i1', and use pmin
to get the minimum value when compared with 4. Then we subset the 'A_B' based on 'i1' and do an integer division with 'i2'. We group by 'grp', get the row index ('.I`) based on the logical conditions and then assign the 'A_BnewNew' to 0. If not needed, the 'grp' can be assigned to NULL.
library(data.table)
iN <- setDT(df1)[, grp := cumsum(A_B!=0)][grp!=0, A_BnewNew := {
i1 <- A_B!=0; i2 <- pmin(sum(!i1),4)
A_B[i1]%/%i2} , by = grp
][, .I[!(A_B ==0 & grp !=0 & (1:.N) <= pmin(5, .N))] , by = grp]$V1
df1[iN, A_BnewNew:=0][, grp := NULL][]
# A_B A_Bnew A_BnewNew
# 1: 0 0 0
# 2: 0 0 0
# 3: 900000 0 0
# 4: 0 300000 300000
# 5: 0 300000 300000
# 6: 0 300000 300000
# 7: 10000 0 0
# 8: 0 5000 5000
# 9: 0 5000 5000
#10: 20000 0 0
#11: 0 5000 5000
#12: 0 5000 5000
#13: 0 5000 5000
#14: 0 5000 5000
#15: 0 0 0
#16: 0 0 0
#17: 0 0 0
df1 <- structure(list(A_B = c(0L, 0L, 900000L, 0L, 0L, 0L, 10000L, 0L,
0L, 20000L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), A_Bnew = c(0L, 0L, 0L,
300000L, 300000L, 300000L, 0L, 5000L, 5000L, 0L, 5000L, 5000L,
5000L, 5000L, 0L, 0L, 0L)), .Names = c("A_B", "A_Bnew"),
class = "data.frame", row.names = c(NA, -17L))