如何在java中解压二进制文件?

Posted

技术标签:

【中文标题】如何在java中解压二进制文件?【英文标题】:How to unpack a binary file in java? 【发布时间】:2014-11-19 20:47:57 【问题描述】:

有人可以帮助我了解如何在 java 中使用下面的代码在 ruby​​ 中进行操作。

下面的 ruby​​ 代码使用 unpack('H*')[0] 将完整的二进制文件内容存储在 ASCII 格式的变量“var”中。

IO.foreach(ARGV[0]) |l| 

        var = l.unpack('H*')[0]

 if File.exists?(ARGV[0])

更新: 嗨,阿鲁。我已经测试了你在下面表格中所说的方式

byte[] bytes = Files.readAllBytes(testFile.toPath());
str = new String(bytes,StandardCharsets.UTF_8);
System.out.println(str); 

但是当我打印变量“str”的内容时,打印输出只显示小方块,就像没有解码内容一样。我想将二进制文件的内容以 ASCII 格式存储在“str”中。

更新 #2: 您好 Aru,我正在尝试将所有二进制文件的内容存储在字节数组中,但我不知道该怎么做。有效 使用“FileUtils.readFileToByteArray(myFile);”但这是一个外部库,有内置选项吗?

File myFile = new File("./Binaryfile");
byte[] binary = FileUtils.readFileToByteArray(myFile); //I have issues here to store in array of bytes all binary content
String hexString = DatatypeConverter.printHexBinary(binary);
System.out.println(hexString); 

更新 #3:

您好 ursa 和 Aru,感谢您的帮助。我已经尝试了您的两种解决方案并且效果很好,但是看到 Files.readAllBytes() 文档 它说这不是为了处理大文件,我要分析的二进制文件超过 2GB :(。我看到你的解决方案的一个选项,阅读 一块一块地。二进制文件中的块由序列 FF65 分隔,所以有没有办法调整你的代码以只处理一个块 基于块分隔符的时间?如果没有,也许有一些外部库。

更新 #4: 您好,我正在尝试修改您的代码,因为我想根据以下内容读取可变大小的块 “Var”的值。

如何设置偏移量以读取代码中的下一个块?

我的意思是, - 在第一次迭代中读取第一个 1024, - 在这一步 Var=500 - 在 2d 迭代中读取接下来的 1024 个字节,从 1024 开始 - Var = 1024-500 = 524 - 在这一步 Var=712 - 在第 3 次迭代中读取接下来的 1024 个字节,从 1548 开始 - Var = 1548-712 = 836 - 等等

是否有类似 read(number of bytes, offset) 之类的方法?

【问题讨论】:

Files.readAllBytes() 从文件中读取所有字节。这是你要找的吗? 嗨,阿鲁。感谢您的回答,但无法正常工作。请在原始问题中查看我的更新。谢谢 我确实在我的帖子中添加了另一个示例,说明如何仅从文件中读取一定数量的字节。 Java Tutorial: Basic I/O 【参考方案1】:

你可以使用commons-codec Hex class + commons-io FileUtils class:

byte[] binary = FileUtils.readFileToByteArray(new File("/Users/user/file.bin");
String hexEncoded = Hex.encodeHex(binary);

但如果你只想阅读 TEXT 文件的内容,你可以使用:

String content = FileUtils.readFileToString(new File("/Users/user/file.txt", "ISO-8859-1");

使用 JRE 7,您可以使用标准类:

public static void main(String[] args) throws Exception 
    Path path = Paths.get("path/to/file");
    byte[] data = Files.readAllBytes(path);

    char[] hexArray = "0123456789ABCDEF".toCharArray();
    char[] hexChars = new char[data.length * 2];
    for ( int j = 0; j < data.length; j++ ) 
        int v = data[j] & 0xFF;
        hexChars[j * 2] = hexArray[v >>> 4];
        hexChars[j * 2 + 1] = hexArray[v & 0x0F];
    
    System.out.println(new String(hexChars));

【讨论】:

你好大熊,谢谢。看来它有效,我需要下载 common-packs.jar 并且我使用 netbeans 位于我的项目文件夹中。在 netbeans 控制台中运行良好,但是当我构建项目时不起作用。 commons-pack.jar 应该放在哪里? Programfiles/java/...里面的某个地方? 这是一个非常广泛的问题,需要单独讨论。你可以从这里开始:***.com/a/4650054/2078908 @Zurix 如果您将库正确添加到 Netbeans 中的项目中,则在构建时应将所有库放在子文件夹 /lib 中并将它们添加到类路径中。但是不需要使用外部库,Java已经内置了这个功能:DatatypeConverter.printHexBinary() 您好 ursa/Aru,感谢您的帮助。请您在原始帖子中看到我的更新#2。我正在尝试按照您的建议使用内置的 DatatypeConverter.printHexBinary(binary),但我遇到了问题。 您好 ursa/Aru,您的两个解决方案都有效,但我发现了另一个问题。请您在原始帖子中查看我的更新 3。非常感谢。【参考方案2】:

这应该做你想做的:

try 
    File inputFile = new File("someFile");
    byte inputBytes[] = Files.readAllBytes(inputFile.toPath());
    String hexCode = DatatypeConverter.printHexBinary(inputBytes);
    System.out.println(hexCode);
 catch (IOException e) 
    System.err.println("Couldn't read file: " + e);

如果您不想一次读取整个文件,也可以这样做。您将需要某种InputStream

File inputFile = new File("C:\\Windows\\explorer.exe");
try (InputStream input = new FileInputStream(inputFile)) 
    byte inputBytes[] = new byte[1024];
    int readBytes;
    // Read until all bytes were read
    while ((readBytes = input.read(inputBytes)) != -1) 
        System.out.printf("%4d bytes were read.\n", readBytes);
        System.out.println(DatatypeConverter.printHexBinary(inputBytes));
    
 catch (FileNotFoundException ex) 
    System.err.println("Couldn't read file: " + ex);
 catch (IOException ex) 
    System.err.println("Error while reading file: " + ex);

【讨论】:

你好阿鲁,它工作得很好。我正在尝试修改您的代码以按顺序读取每个块。但是这些块的大小是可变的。请您在原始帖子中看到我的更新。非常感谢你的帮助。是开始工作的最后一步。

以上是关于如何在java中解压二进制文件?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 java 中读取二进制 .Chn 格式文件?

如何实现用java语言读取二进制文件的内容解析后存储在链表里

JAVA如何将二进制数转换成文件?

java如何把一个以文本存储的文件转化为二进制文件

如何在 Windows 上安装 OpenJDK 11?

java中如何把一个图片转换成二进制流存入到类中啊?