Save data every t time units in R

53 Views Asked by At

I want to do move through a loop and save a value at particular time intervals. I was thinking of something with this form:

    t <- 0
    t_end <- 10
    time_step <- 0.01
    record_interval <- 1
    while (t <= t_end){
        if (t %% record_interval == 0) print(t)
        t <- t + time_step
    }

But of course doing it this way fails due to machine precision issues.

I can do:

if (isTRUE(all.equal(t %% record_interval,0, tolerance = time_step*0.1))) { ...

But even this fails because sometimes it gives a modulo of record_interval rather than 0.

So, I can run my code with an or statement, using the above and also checking if the modulo is equal to record_interval, but that's incredibly ugly. I am sure there is an obvious, easy way to solve this problem but I am at a loss. I don't want to introduce an unnecessary integer counter (the all.equal part works, it's just not pretty, so that seems less bad), and I want to be able to change time_step and record_interval depending upon needs.

2

There are 2 best solutions below

3
tassones On

One option would be to use tidyverse to create a new column called of your hundredths value, filter the data to the interval you want, then remove the new column.

# Load tidyverse
library(tidyverse)

# Create example data
dat <- data.frame(
  t = seq(0,10,0.01)
)

head(dat)
#>      t
#> 1 0.00
#> 2 0.01
#> 3 0.02
#> 4 0.03
#> 5 0.04
#> 6 0.05

# Create new column, filter the time interval you want, then remove the new column
dat2 <- dat %>%
  mutate(hundredths = floor(t * 100) %% 10) %>%
  filter(hundredths == 7) %>%
  select(-hundredths)

head(dat2)
#>      t
#> 1 0.07
#> 2 0.17
#> 3 0.27
#> 4 0.37
#> 5 0.47
#> 6 0.57

Created on 2023-12-01 with reprex v2.0.2

0
dchauri On

You can get around the precision issue by just adding a rolling variable and resetting it when you hit the point you save the value:

t_rolling <- t_rolling + time_step; if (t_rolling > record_interval) { print(t); t_rolling <- 0 }

Thanks for the helpful responses!