6

假设我在 32 GB 的服务器上有一个 4 GB 的数据集。

我可以将所有这些读入 R,创建一个 data.table 全局变量,并让我的所有函数都使用该全局变量作为一种内存数据库。但是,当我退出 R 并重新启动时,我必须再次从磁盘读取它。即使使用智能磁盘缓存策略(保存/加载或 R.cache),我也有 10 秒左右的延迟来获取数据。复制该数据大约需要 4 秒。

有没有一种好方法可以在 R 会话退出后将其缓存在内存中?

想到了几件事,RServe、redis/Rredis、Memcache、多核...... Shiny-Server 和 Rstudio-Server 似乎也有解决这个问题的方法。

但话又说回来,在我看来,也许 data.table 可以提供此功能,因为它似乎无论如何都会将数据移动到 R 的内存块之外。这将是理想的,因为它不需要任何数据复制、重组等。

更新:

我进行了一些更详细的测试,我同意下面的评论,我可能没有太多可抱怨的。

但这里有一些其他人可能会觉得有用的数字。我有一个 32GB 的服务器。我创建了一个 4GB 大小的 data.table。根据 gc() 并查看顶部,它似乎使用了大约 15GB 的峰值内存,其中包括制作一份数据副本。我觉得这很好。

我用 save() 写入磁盘,删除了对象并使用 load() 重新制作它。这分别花费了 17 秒和 10 秒。

我对 R.cache 包做了同样的事情,这实际上更慢。23 和 14 秒。

然而,这两个重新加载时间都非常快。load() 方法给了我 357 MB/s 的传输速率。相比之下,复制需要 4.6 秒。这是一个虚拟服务器。不确定它有什么样的存储或缓存对读取速度的影响有多大。

4

3 回答 3

5

非常正确:data.table还没有到磁盘表。与此同时,一些选项是:

  • 不要退出 R。让它在服务器上运行并使用 svSocket 来evalServer()处理它,如data.table主页上的视频所示。或您提到的其他类似选项。

  • 使用数据库来实现持久性,例如 SQL 或任何其他 noSQL 数据库。

  • 如果您有大的分隔文件,那么最近有人报告fread()说它比load(). 但是用compress=FALSE. 此外,我们刚刚推fwrite送到最新的开发版本(1.9.7,用于devtools::install_github("Rdatatable/data.table")安装),据报道该版本的写入时间与 native 相当save

  • ff,bigmemorysqldf, 也是。请参阅 HPC 任务视图的“大内存和内存不足数据”部分。

data.table正在使用的企业中,我的猜测是它目前主要是从其他一些持久性数据库中获取数据。这些企业可能:

  • 使用 64 位,比如 16GB、64GB 或 128GB 的​​ RAM。这些天 RAM 很便宜。(但我意识到这并没有解决持久性问题。)

编写内部结构时考虑了磁盘表。但不要屏住呼吸!

于 2013-03-27T22:52:40.283 回答
3

根据您的数据集的外观,您可能会考虑使用包 ff。如果您将数据集保存为 ffdf,它将存储在磁盘上,但您仍然可以从 R 访问数据。ff 对象具有虚拟部分和物理部分。物理部分是磁盘上的数据,虚拟部分为您提供有关数据的信息。

要在 R 中加载此数据集,您只需加载数据集的虚拟部分,该部分要小得多,可能只有几 Kb,这取决于您是否有大量带有因子的数据。因此,这将在几毫秒而不是几秒内将您的数据加载到 R 中,同时仍然可以访问物理数据来进行处理。

于 2013-03-28T08:58:49.670 回答
3

如果你真的需要在计算会话之间因为一些奇怪的原因退出 R 并且服务器没有重新启动,那么只需在 RAM 中创建一个 4 GB ramdisk 并将数据存储在那里。与任何 SAS 或 SSD 驱动器相比,将数据从 RAM 加载到 RAM 会快得多:)

这可以在 Linux 上很容易地解决,只需将此行添加到/etc/fstab

none  /data  tmpfs  nodev,nosuid,noatime,size=5000M,mode=1777  0  0
于 2013-03-27T23:40:15.387 回答