【问题标题】:How to manipulate *huge* amounts of data如何操作*大量*数据
【发布时间】:2011-02-07 11:15:47
【问题描述】:

我遇到以下问题。我需要存储 大量 信息 (~32 GB) 并能够尽可能快地操作它。我想知道最好的方法是什么(编程语言 + 操作系统 + 任何你认为重要的组合)。

我使用的信息结构是双精度浮点数(8 字节)的 4D 数组 (NxNxNxN)。现在我的解决方案是将 4D 数组分割成 2D 数组,并将它们存储在我计算机 HDD 中的单独文件中。这真的很慢,而且对数据的操作令人难以忍受,所以这根本不是解决方案!

我正在考虑搬到我所在国家/地区的超级计算设施并将所有信息存储在 RAM 中,但我不确定如何实现应用程序以利用它(我不是专业程序员,所以任何书籍/参考资料都会对我有很大帮助)。

我正在考虑的另一种解决方案是购买具有大量 RAM 的专用服务器,但我不确定这是否能解决问题。所以现在我的无知并没有让我选择最好的方法。

如果你遇到这种情况,你会怎么做?我愿意接受任何想法。

提前致谢!


编辑:很抱歉没有提供足够的信息,我会尝试更具体的。

我正在存储一个离散的 4D 数学函数。我想要执行的操作包括数组的转置(更改 b[i,j,k,l] = a[j,i,k,l] 等)、数组乘法等。

由于这是对提议实验的模拟,因此这些操作只会应用一次。一旦得到结果,就不需要对数据进行更多的操作了。


编辑(2):

我还希望将来能够存储更多信息,因此该解决方案应该具有某种可扩展性。当前的 32 GB 目标是因为我想要拥有 N=256 个点的数组,但如果我可以使用 N=512 会更好(这意味着 512 GB 来存储它!)。

【问题讨论】:

  • 这在很大程度上取决于您打算如何处理这些数据。您能更明确地说明您的操作吗?
  • 32GB 不算多。大型强子对撞机 ATLAS 实验的输出(峰值速率)只有 5 分钟多一点……
  • 补充一下 Chris 所说的,处理大量数据有不同的方法,其中一些更喜欢某些用途而不是其他用途。例如,过多的分页会降低您的性能,为了避免这种情况,有必要知道您将如何访问数据。
  • 您是否有 64 位系统,内存 >32GB?你能得到一个吗?您的转换是计算密集型的吗?您的应用程序可以分发到机器集群吗? “快”有多快?
  • @Donal:我确信 ATLAS 的人的预算与该数字相符 :-) @David+@Stephen:性能很重要,但不是那么重要。我可以先尝试 N=64,一旦正确调试,我可以运行 N=256,然后等两天?现在的主要问题是我无法将它存储在快速(比 HDD 更快)的存储设备中。我可以访问我大学中的一个集群,以及我居住的城市中另一个更强大的集群(0.12 欧元/小时)。关于它是否可以分发到集群,不知道,这可能是一个解决方案。我怎么知道?

标签: arrays memory memory-management hpc


【解决方案1】:

任何体面的答案都取决于您需要如何访问数据。随机访问?顺序访问?

32GB 并不是那么大。

您需要多久处理一次数据?每(生命周期 | 年 | 天 | 小时 | 纳秒)一次?通常,事情只需要完成一次。这对您优化解决方案所需的时间有着深远的影响。

你将执行什么样的运算(你提到了乘法)?是否可以将数据拆分为块,以便一组操作所需的所有数据都包含在一个块中?这样可以更轻松地将其拆分为并行执行。

您现在购买的大多数计算机都有足够的 RAM 来容纳 32GB 的内存。你不需要一台超级计算机。

【讨论】:

  • 我非常怀疑是否有任何家用电脑可以容纳 32GB 的内存。但我明白你的意思,如果是 64 位操作系统,打开 32GB 文件不会使计算机过载。 32GB 中的大部分将保存在交换空间中
  • @thecoshman:是的。我搞砸了。但是快进 5 年和 32GB 将是 蹩脚 :) 我有点困惑,在计算出他需要大约 256GB 之后,我想,等一下,256 ?我的笔记本电脑里有 3TB。但这与事实相差 3 个数量级......
  • 有。如今,一台普通的家用计算机可以容纳 16GB 的内存。如果不经常发生,添加虚拟内存(快速磁盘、SSD)并“仅在内存中”处理 32gb 实际上是可行的。如今,服务器主板可以轻松容纳 128GB,但价格要贵得多。
【解决方案2】:

正如 Chris 指出的那样,您将如何处理这些数据。

此外,我认为将它存储在(关系)数据库中会比从硬盘驱动器读取它更快,因为 RDBMS 会为您执行一些优化,例如缓存。

【讨论】:

  • 我不知道任何不缓存高清的现代操作系统。
  • 这是一个 4 维浮点数组,当您有 4 个已知索引时,使用 RDBMS 似乎不是最佳选择。
【解决方案3】:

如果没有更多信息,如果您需要尽可能快地访问所有数据,我会使用 C 作为您的编程语言,使用某种风格的 *nix 作为 O/S,并购买 RAM,现在它相对便宜。这也取决于您熟悉的内容,您也可以走windows路线。但正如其他人所提到的,这将取决于您如何使用这些数据。

【讨论】:

    【解决方案4】:

    整个数据库技术是关于处理无法放入 RAM 的大量数据,因此这可能是您的起点(例如,获取一本好的 dbms 原理书并阅读有关索引、查询执行等方面的知识)。 很大程度上取决于您需要如何访问数据 - 如果您绝对需要跳转并访问随机的信息位,那么您就有麻烦了,但也许您可以构建数据处理,以便您沿着一个扫描它轴(尺寸)。然后你可以使用更小的缓冲区,不断地转储已经处理过的数据并读取新的数据。

    【讨论】:

      【解决方案5】:

      亚马逊的“High Memory Extra Large Instance”只有$1.20/hr,有34 GB of memory。假设您没有经常运行此程序,您可能会发现它很有用..

      【讨论】:

      • 32 GB 是我将使用的最小容量,我很想找到一个可扩展的解决方案,以便将来能够使用更多内存(256 GB?)。
      • 如果您查看我链接到的第二页,亚马逊的内存最高可达 68 GB,而且价格仍然合理(同样,只要您不经常使用它)。跨度>
      • 租用功能强大的硬件而不是花时间尝试优化问题是值得说的。 10 小时 1.20 美元/小时是 12 美元,这比该领域任何有能力的人收取的最低咨询费要低得多。
      • 特别是在罕见的情况下(即每月一次左右)。
      【解决方案6】:

      如果您可以将问题表示为 MapReduce,请考虑针对磁盘访问优化的集群系统,例如 Hadoop。

      您的描述听起来更加数学密集,在这种情况下,您可能希望一次将所有数据存储在内存中。单机32GB内存也不是不合理; Amazon EC2 提供高达 68 GB 的虚拟服务器。

      【讨论】:

        【解决方案7】:

        我建议的第一件事是选择一种面向对象的语言,并开发或找到一个类,让您可以操作 4-D 数组而无需关心它的实际实现方式。

        这个类的实际实现可能会使用内存映射文件,因为它可以从低功耗开发机器扩展到您想要运行生产代码的实际机器(我假设您会想要运行多次,因此性能很重要——如果你可以让它在一夜之间运行,那么一台消费类 PC 可能就足够了。

        最后,一旦我的算法和数据调试完毕,我会考虑在一台可以将所有数据保存在内存中的机器上争取时间。例如,Amazon EC2 将以每小时 2.40 美元的价格为您提供一台具有 68 GB 内存的机器(如果您使用的是现场实例,则更低)。

        【讨论】:

        • 实际上,没有。编译/解释的角度可能与相关任务无关(查看 NumPy 等)。
        • @Daren:是的 - 当最大的延迟是在磁盘上存取数据时,一些额外的 CPU 时间可能根本不重要。
        • @Daren Thomas - 实际上,是的。虽然 NumPy 对于预先编写的数组操作工具可能是一个非常好的选择(并且应该是一个独立的答案),但您会注意到它的部分内容是用 C 编写的:sourceforge.net/projects/numpy/develop
        • @David Thornley - 同意将数据移入和移出磁盘将是一个大问题,这就是为什么我提出了一个让操作系统完成工作的解决方案。
        • @Anon:除了操作系统不会聪明地预测接下来将访问哪些值,并且会尽其所能将数组移入和移出内存。对于某些操作,这只是桃子。对于其他人,它会导致颠簸。
        【解决方案8】:

        对于转置,实际上只是改变您对索引是什么的理解会更快。我的意思是,您将数据留在原处,而是将更改 b[i][j][k][l] 的访问器委托包装到获取(或更新)a[j][i][k][l] 的请求中。

        【讨论】:

        • @Donal:没错,但是如果我将数组分割成二维数组,比如 a34[i,j] = a[i,j,3,4] 和 b25[k,l] = [2,5,k,l],然后我需要对a[i,5,k,4]进行操作,然后我必须访问所有文件以获得其中包含的等效信息只有一个文件。这就是减慢操作速度的原因。
        【解决方案9】:

        可以通过这个程序解决吗?

        首先创建M子进程并并行执行。每个进程将在集群的专用核心中运行,并将阵列的一些信息加载到该核心的 RAM 中。

        父进程将成为数组的管理器,调用(或连接)相应的子进程以获取某些数据块。

        这会比 HDD 存储方法更快吗?还是我在用大锤敲碎坚果?

        【讨论】:

        • 只要他们都访问不同的硬盘驱动器,这可以工作。如果都是同一个硬盘驱动器,它只会减慢你的速度。
        • @Bredan:这个想法是让内核将信息加载到 RAM 中,因此在数学运算期间没有硬盘访问。反正核心是独立的,应该没问题。
        【解决方案10】:

        到目前为止,有很多非常不同的答案。上面提到了两个很好的起点。 David 建议了一些硬件,有人提到学习 C。这两个都是好点。

        C 将在速度和直接内存分页方面为您提供所需。您要做的最后一件事是对数据执行线性搜索。那会很慢 - 慢 - 慢。

        确定您的工作流程 - 如果您的工作流程是线性的,那是一回事。如果工作流程不是线性的,我会设计一个二叉树来引用内存中的页面。互联网上有大量关于 B 树的信息。此外,这些 B 树在 C 中将更容易使用,因为您还可以设置和操作内存分页。

        【讨论】:

        • 我不太确定你所说的一切(我不是程序员类型),但我理解的部分听起来很合理。硬件意味着要花一些钱在:1)SSD驱动器,2)计算时间。这是一个很好的补丁,但不是我正在寻找的可扩展解决方案。另一种方法是学习 C 能够随机访问文件以提高速度,尊重当前的线性访问方式。这听起来更像,但这意味着我必须花时间学习(这不一定是坏事:)
        【解决方案11】:

        根据您的使用情况,一些数学和物理问题往往大多为零(例如,有限元模型)。如果您希望这适用于您的数据,则可以通过使用稀疏矩阵而不是将所有这些零实际存储在内存或磁盘中来节省空间。

        查看维基百科的描述,并确定这是否能满足您的需求: http://en.wikipedia.org/wiki/Sparse_matrix

        【讨论】:

        • 无法重复。
        • 这是一个很好的建议,但不适用于这种情况。事实上,我尝试拟合数据,使空值的数量最少!
        【解决方案12】:

        这是另一个想法:

        尝试使用 SSD 来存储您的数据。由于您要抓取非常少量的随机数据,因此 SSD 可能会快得多。

        【讨论】:

        • 这是我想过的,但我不确定它是否会足够减少执行时间。我在常规 HDD 中使用 N=256 进行了测试,大约花了一个月的时间。我认为这不会少于,什么?,两周?但它仍然是一个很好的混合解决方案(迁移到 Python,甚至更好,C)。
        • 我了解到,对于随机访问,SSD 的速度要快得多。这张图显示了英特尔的 SSD 的性能(我认为——很难说硬盘的性能有多差)比硬盘快 100 倍左右:anandtech.com/show/2738/25 即使是最保守的固态硬盘也至少快 20 倍。
        • RealSSD 的磁盘执行 40k IOPS。这对于随机访问来说是非常重要的。就像 100 到 1000 倍。而且它们变得更快。
        【解决方案13】:

        如何处理大量数据通常围绕以下因素展开:

        • 数据访问顺序/引用位置:能否将数据分离成独立的块,然后独立处理或以串行/顺序的方式处理 vs. 随机访问数据很少或没有订单?

        • CPU 与 I/O 限制:处理时间是花在计算数据上还是从/向存储读取/写入数据上?

        • 处理频率:数据是否只处理一次、每隔几周、每天等?

        如果数据访问顺序本质上是随机的,您将需要访问尽可能多的 RAM 和/或找到至少部分组织顺序的方法,以便不需要太多的数据同时记忆。一旦超出物理 RAM 限制并发生大量交换,虚拟内存系统就会非常快变慢。解决问题的这方面可能是最关键的问题。

        除了上面的数据访问顺序问题,我认为您的问题没有重大的 I/O 问题。在当前的计算机系统上,读取/写入 32 GB 通常以分钟为单位,即使数据大小达到 TB 也不会超过几个小时。

        编程语言选择实际上不是关键,只要它是一种具有良好优化编译器和体面本机库的编译语言:C++、C、C# 或 Java 都是合理的选择。我从事过的计算和 I/O 密集度最高的软件实际上是用 Java 编写的,并部署在具有数千个 CPU 内核的高性能超级计算集群上。

        【讨论】:

          【解决方案14】:

          您可能想尝试使用 mmap 而不是将数据读入内存,但我不确定它是否适用于 32Gb 文件。

          【讨论】:

            猜你喜欢
            • 2023-04-07
            • 1970-01-01
            • 1970-01-01
            • 2017-09-29
            • 1970-01-01
            • 1970-01-01
            • 2014-12-19
            • 2017-10-27
            • 2019-10-19
            相关资源
            最近更新 更多