Home > Mobile >  How can I rollapply or slide in a data frame in R with sliding width as well?
How can I rollapply or slide in a data frame in R with sliding width as well?

Time:10-21

I have data frame in R that looks like this :

a b
8 -16
19 -26
30 -36
41 -46
52 -56

I want to slide it or rollapply it with width 3 in both columns and calculate the the sum of the two minimum.

BUT.!!!!

I want progressively go tho width 3 starting with width (3 1)/2 = 2 and then go to width 3.

In my example must start with the first 2 rows:

a b
8 -16
19 -26

result must be the sum of the minimums of columns a and b 8 (-26)=-18 next

a b
8 -16
19 -26
30 -36

result must be the sum of the minimums of columns a and b 8 (-36)=-28

next

a b
19 -26
30 -36
41 -46

19-46 = -27

next

a b
30 -36
41 -46
52 -56

30-56 = -26

and last

a b
41 -46
52 -56

41-56=-15.

The width must be 2,3,3,3,2.

In general if this data frame had 100 rows with window 13 it will start from top to bottom with window (or width) (13 1)/2 = 7, then it will continue to 8,9,10,12,13,13,...,13,12,11,10,9,8,7.

How can I do this in R ?

library(tidyverse)

a = c(800,1900,3000,4100,5200)
b = c(-1600,-2600,-3600,-4600,-5600)

w = tibble(a,b)


CodePudding user response:

We may use rollapply from zoo with partial = TRUE to loop over the sequence of rows, subset the data based on the index, get the min from columns (sapply(..., min)) and get the sum of those

library(zoo)
wd <- 3
rollapply(seq_len(nrow(df1)), FUN = function(i) sum(sapply(df1[i,],
            min)), width = wd, partial = TRUE)
[1] -18 -28 -27 -26 -15

data

df1 <- structure(list(a = c(8L, 19L, 30L, 41L, 52L), b = c(-16L, -26L, 
-36L, -46L, -56L)), class = "data.frame", row.names = c(NA, -5L
))

CodePudding user response:

in Base R you could do:

fn <- function(x, window){
  na <- rep(NA, ceiling((window-1)/2))
  apply(embed(c(na, x, na), window),1, min, na.rm = TRUE)
}

rowSums(sapply(df,fn, 3))

[1] -18 -28 -27 -26 -15
  • Related