与在RStudio中使用saveRDS有关的时序问题

时间:2019-03-31 23:25:23

标签: r rstudio

在执行循环之前调用saveRDS会导致循环时序不一致。这仅在使用RStudio时明显。使用Rscript从命令行运行相同脚本时,该问题不存在。这可能是RStudio中I / O刷新延迟的结果。

  • 其他人注意到了这种行为吗?
  • 是否有一种方法可以在saveRDS调用后强制进行I / O刷新?

在64位Ubuntu 18.04LTS上使用RStudio 1.1.463,R 3.5.2。

我通过在代码执行之前调用gc()并使用gcinfo启用gc消息来确保未触发gc,从而消除了垃圾收集器的问题。我还尝试使用cmpfun预编译该函数;这也无济于事。

以下代码可用于重现该问题。

loop.test <- function() {
  t <- c()
  t0 <- Sys.time()
  for (i in 1:10) {
    t <- c(t, Sys.time() - t0)
    Sys.sleep(0.01)
  }

  dt <- round(1000 * diff(t), 1)
  print(dt)
  print(summary(dt))
}

saveRDS(1:10, 'garb.rds')

loop.test()

代码将产生以下输出(以毫秒为单位的循环时间):

[1]  10.1  10.1  10.2  10.2 275.4  10.2  10.1  10.2  10.2

   Min. 1st Qu.  Median    Mean 3rd Qu.    Max. 
  10.10   10.10   10.20   39.63   10.20  275.40

请注意,较大的延迟不会总是出现在同一迭代中。

在代码中删除saveRDS调用将始终产生一致的(接近10ms)循环定时。

无论是否有saveRDS行,都可以通过Rscript从命令行运行代码。

1 个答案:

答案 0 :(得分:0)

这是RStudio的回应:

一种可能性:RStudio在R“空闲”期间(即:当R调用R_ProcessEvents时)进行一些后台工作,我认为项目文件索引就是其中之一。 RStudio为这些任务注册了文件监视器,因此创建文件可能会使RStudio在后台进行一些重新索引工作。

我验证了将saveRDS()调用中的保存目录更改为项目目录之外的内容可以避免计时问题。因此,我认为这支持文件索引理论。 RStudio v1.2预览在较小程度上显示了此行为,因此空闲处理实现中可能有所更改,但是我对此没有进一步的信息。 RStudio伙计们打开了一个错误报告来解决此问题,因此希望该修复程序将很快发布。

因此,目前,一些解决方法是:

  1. 在调用saveRDS()之后,以足够的延迟调用Sys.sleep(),以允许进行重新索引操作。
  2. 将saveRDS()指向当前项目目录之外的文件,以防止重新编制索引。