简体   繁体   English

C : 从二进制文件中读取字节

[英]C : Reading bytes from binary file

I am currently trying to read 256 bytes from a binary file and not getting any output (or errors) when running my program.我目前正在尝试从二进制文件中读取 256 个字节,并且在运行我的程序时没有得到任何输出(或错误)。 I am a little confused where I am going wrong on this.我有点困惑我哪里出错了。 Attempting to read each byte as a char and store as a char array of length 256. I have reviewed similar questions on SO already and haven't had any luck so far.尝试将每个byte读取为char并存储为长度为 256 的字符数组。我已经查看了关于 SO 的类似问题,到目前为止还没有任何运气。 Simplified version of my code below:我的代码的简化版本如下:

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char *argv[]){
    FILE *binary = fopen(argv[1], "rb");
    char bytesFromBinary[256];

    fread(&bytesFromBinary, 1, 256, binary);
    printf("%s", bytesFromBinary);
    return 0;
}

A basic use of fread will check the return against the number of bytes expected to validate you read what you intended to read. fread的基本用法将根据预期的字节数检查返回值,以验证您阅读了您打算阅读的内容。 Saving the return allows you to handle partial reads as well.保存返回也允许您处理部分读取。

The following minimal example reads 16-bytes at a time from the file given as the first argument (or stdin by default if no file is given) into buf and then outputs each value to stdout in hex-format.下面的最小示例一次从作为第一个参数给出的文件(如果没有给出文件,则默认为stdin读取 16 个字节到buf ,然后将每个值以十六进制格式输出到stdout

#include <stdio.h>

#define BUFSZ 16

int main (int argc, char **argv) {

    unsigned char buf[BUFSZ] = {0};
    size_t bytes = 0, i, readsz = sizeof buf;
    FILE *fp = argc > 1 ? fopen (argv[1], "rb") : stdin;

    if (!fp) {
        fprintf (stderr, "error: file open failed '%s'.\n", argv[1]);
        return 1;
    }

    /* read/output BUFSZ bytes at a time */
    while ((bytes = fread (buf, sizeof *buf, readsz, fp)) == readsz) {
        for (i = 0; i < readsz; i++)
            printf (" 0x%02x", buf[i]);
        putchar ('\n');
    }
    for (i = 0; i < bytes; i++) /* output final partial buf */
        printf (" 0x%02x", buf[i]);
    putchar ('\n');

    if (fp != stdin)
        fclose (fp);

    return 0;
}

(note: bytes == readsz only when the size parameter to fread is 1 . The return is the number of items read and each item is only equal to 1 for char type values) (注意: bytes == readsz仅当freadsize参数为1 。返回的是读取的items数,对于char类型值,每个项目仅等于1

Example Use/Output示例使用/输出

$ echo "A quick brown fox jumps over the lazy dog" | ./bin/fread_write_hex
 0x41 0x20 0x71 0x75 0x69 0x63 0x6b 0x20 0x62 0x72 0x6f 0x77 0x6e 0x20 0x66 0x6f
 0x78 0x20 0x6a 0x75 0x6d 0x70 0x73 0x20 0x6f 0x76 0x65 0x72 0x20 0x74 0x68 0x65
 0x20 0x6c 0x61 0x7a 0x79 0x20 0x64 0x6f 0x67 0x0a

Look over the example and let me know if you have any questions.查看示例,如果您有任何问题,请告诉我。

You have not declared a long enough variable.您还没有声明足够长的变量。

Your declaration char bytesFromBinary[256];您的声明char bytesFromBinary[256]; reserves 256 bytes, and fread fills all 256 bytes.保留 256 个字节, fread填充所有 256 个字节。 There is no trailing '\\0' and there is no space for it, so whatever happens to be next in memory gets overwritten/destroyed.没有尾随'\\0'并且它没有空间,因此内存中接下来发生的任何事情都会被覆盖/破坏。 That already will result in all kind of random errors and crashes.这已经会导致各种随机错误和崩溃。

Then, in printf, you try to print it, and the function will keep running through memory until it happens to encounter a '\\0' to stop it, so if the program makes it there, you would get a printout of memory, maybe short, maybe thousands of (non-printable) characters long.然后,在 printf 中,您尝试打印它,该函数将继续在内存中运行,直到碰巧遇到'\\0'来停止它,因此如果程序到达那里,您将得到内存的打印输出,也许短,可能有数千个(不可打印)字符长。

You need to declare the variable always one longer, to have space for the trailing '\\0' : char bytesFromBinary[257];您需要始终将变量声明为一个更长的时间,以便为尾随的'\\0' char bytesFromBinary[257];空间: char bytesFromBinary[257]; . . even better is to use sizeof(var)-1 in fread, or use a constant for the desired length and declare it with +1.更好的是在 fread 中使用sizeof(var)-1 ,或者使用一个常量来获得所需的长度并用 +1 声明它。

It fails because you are trying printing a block of bytes as a C-style string.它失败是因为您尝试将字节块打印为 C 样式字符串。

There are two kinds of files: binary file and text file.有两种文件:二进制文件和文本文件。 To read/write a file, you should open it in the corresponding mode.要读/写文件,您应该以相应的模式打开它。

If your file is created in this way:如果您的文件是以这种方式创建的:

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char *argv[])
{
    FILE *binary = fopen("file.txt", "wbx");
    if(!binary)
    {
        perror("fopen()");
        exit(EXIT_FAILURE);
    }
    char bytesToBinary[256] = ":-)";

    fwrite(bytesToBinary, 1, 256, binary);
    fclose(binary);
    return 0;
}

Your code should be successful.你的代码应该是成功的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM