【问题标题】:Efficiently read binary data into int[]有效地将二进制数据读入 int[]
【发布时间】:2014-12-20 14:00:02
【问题描述】:

我在一个文件(32 位整数值列表)中有二进制数据,我需要有效地进入一个 int 数组。除了将数据加载到 byte[] 中,然后一次将其转换为 int[] 一个元素之外,我看不到任何其他方法。这对于我需要加载的数据量来说太慢了。在实际手机上进行转换大约需要 3 秒。从 byte[] 中的文件读取数据几乎是瞬时的。

是否有任何库使用本地方法从文件中读取 int[],或将 byte[] 转换为 int[]?

【问题讨论】:

  • 您确定是转换花费了大部分时间吗?我不相信。我先看看 I/O。
  • 是的,我已经记录了操作,并且通过数组的迭代一直都是。事实上,我已经通过编写一个本地方法来解决这个问题。在 C++ 中,转换数据是一个简单的转换。
  • 嘿克里斯!您认为您可以将代码粘贴到此处,或者粘贴到 pastebin.com,然后在此处发布指向它的链接吗?我相信这一小段代码对 Android 开发者来说可能是一个很好的增强。你是否也尝试过我写的 NIO 包,如果是的话:你有一些性能比较吗?我会对他们很感兴趣。 :)

标签: java android


【解决方案1】:

你有没有尝试过这样的事情:

File file = new File("binary.file");
FileInputStream fin = new FileInputStream(file);
BufferedInputStream bin = new BufferedInputStream(fin);
DataInputStream din = new DataInputStream(bin);

int count = (int) (file.length() / 4);
int[] values = new int[count];
for (int i = 0; i < count; i++) {
    values[i] = din.readInt();
}

即使在手机上,这也应该相对较快,除非您只是处理一个巨大的文件。

【讨论】:

  • 好点,它只适用于大端整数。通常它用于传输,但是如果需要,OP 可以参考 stackoverflow.com/questions/5712066/… 来读取 little-endian。
  • @road to yamburg - 假设 OP 正在尝试读取在手机本身上创建的二进制文件或由另一个 Java / Android 平台上的某个应用程序创建的二进制文件并不是不合理的......并且文件将是大端的。
  • 问题是我的数组大小为 1.5MB,像这样对 Java 中元素的任何迭代都太慢了。
【解决方案2】:

你试过NIO package的类吗?类ByteBuffer 有一个方法asIntBuffer(),您可以在其中获得ByteBuffer 的IntBuffer 视图。然后你应该可以通过调用get(int[] dst)来获取整数形式的内容。

使用file channels可以获得初始ByteBuffer。

【讨论】:

  • 创建 IntBuffer 涉及的操作量非常大。我想知道手动 a
  • 我试图使用 NIO 包,但是使用 array() 方法遇到了麻烦,该方法对于从 byte[] 创建的缓冲区不存在。但看起来 get() 就是答案。
  • @road to yamburg:这可能是。但是字节缓冲区的实际实现在本机代码中的可能性很高,因此速度要快得多。事实上,我相信 Android 的 NIO 包是原生完成的——我在那里找不到 Java 中的有效字节缓冲区实现。 @Chris:完全正确-您不能使用 array() 方法,因为您的 IntBuffer 不是由 int[] 数组支持,而是由 byte[] 数组支持。 developer.android.com/reference/java/nio/… 上的 array() 文档清楚地说明了这一点。 :)
【解决方案3】:

我使用序列化/反序列化、DataInputStream 与 ObjectInputStream 进行了相当仔细的实验​​,两者都基于 ByteArrayInputStream 以避免 IO 影响。对于一百万个 int,readObject 大约是 20 毫秒,readInt 大约是 116。一百万个 int 数组的序列化开销是 27 个字节。

话虽如此,对象序列化有点邪恶,你必须用 Java 程序写出数据。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-09-07
    • 1970-01-01
    • 2018-08-16
    • 2021-07-28
    • 2015-04-20
    • 2012-01-17
    • 2022-01-11
    相关资源
    最近更新 更多