【问题标题】:Buffer a large file; BufferedInputStream limited to 2gb; Arrays limited to 2^31 bytes缓冲一个大文件; BufferedInputStream 限制为 2gb;数组限制为 2^31 字节
【发布时间】:2008-09-26 21:09:19
【问题描述】:

我正在按顺序处理一个大文件,我想将其中的一大块保存在内存中,在 64 位系统上可用 16gb 内存。

一种快速而肮脏的方法是做到这一点,只是将输入流包装成一个缓冲的输入流,不幸的是,这只给了我一个 2gb 的缓冲区。我想在内存中保留更多内容,我有什么替代方案?

【问题讨论】:

标签: java 64-bit buffer bufferedinputstream


【解决方案1】:

让操作系统处理文件的缓冲怎么样?您是否检查过不将整个文件复制到 JVM 内存中对性能的影响是什么?

编辑:然后您可以使用 RandomAccessFile 或 FileChannel 将文件的必要部分有效地读入 JVM 内存。

【讨论】:

  • 最初它没有被缓冲,java会读一点,处理它,然后再读一点。每次读取都会发送一个 IO 请求,等待 io 完成。缓冲输入会线性增加速度,缓冲区越大,处理速度越快。
  • 看看Java NIO,它可以执行更高效的异步文件I/O操作。请参阅我对您问题的评论中的链接 - 它对各种方法进行了很好的比较。
【解决方案2】:

你考虑过 java.nio 中的 MappedByteBuffer 吗?它在我头上,但也许这就是你要找的。​​p>

【讨论】:

  • 我也是这么认为的,但看起来 ByteBuffer 的后备缓冲区仍然是一个普通缓冲区,因此它与原始缓冲区具有相同的限制。跨度>
  • 有两种缓冲区,一种使用字节数组,另一种(直接)使用 Java 堆外的固定位置。不幸的是,neight 可以超过 2GB。这目前在“更多 NIO 功能”(可能是 JDK7)中没有得到解决。投票给它。 bugs.sun.com/bugdatabase/view_bug.do?bug_id=6347833
【解决方案3】:

我怀疑一次缓冲超过 2gb 是否会是一个巨大的胜利。根据您正在执行的处理量,您可能能够以几乎与处理速度一样快的速度阅读。为了加快速度,您可以尝试使用双线程生产者-消费者模型(一个线程读取文件并将数据交给另一个线程进行处理)。

【讨论】:

    【解决方案4】:

    操作系统将尽可能多地缓存文件,因此试图智取缓存管理器可能不会让您获得太多。

    从性能的角度来看,将字节保留在 JVM 之外会为您提供更好的服务(在操作系统和 JVM 之间传输大量数据相对较慢)。您可以通过使用由直接内存块支持的 MappedByteBuffer 来实现此目标。

    这是一篇相关的文章类型:article

    【讨论】:

      【解决方案5】:

      我认为有 64 位 JVM 将支持非标准限制。

      您可以尝试缓冲块。

      【讨论】:

        猜你喜欢
        • 2021-04-01
        • 2017-05-05
        • 1970-01-01
        • 2021-09-02
        • 2020-05-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多