【问题标题】:CS50 - Recovery - Manipulating Card.raw PSET3CS50 - 恢复 - 操作 Card.raw PSET3
【发布时间】:2019-02-16 17:56:17
【问题描述】:

所以我是一个在 C 方面苦苦挣扎(真的溺水)的新手,试图通过 CS50 努力工作。我正在进行“恢复”练习,试图从 card.raw 文件中恢复 jpeg。通过谷歌搜索得知,通过在终端输入 xxd -l 2400 card.raw (char is 'L'),可以在终端显示字节 0-2384(含),格式如下:

0000000: 0000 0000 0000 0000 0000 0000 0000 0000 ....

0000950: 0fe0 c11b e555 8f20 33cc fbfe 559e 8eee .....U. 3...U...

Q1:我想使用 printf 显示前 32 个字节(全为 0)(这样我就可以验证正在读取的内容)。我的程序编译,但什么也没显示。 (当然,一旦我有这个工作,我会改变它以显示更多字节,因为我知道第一个 jpeg 从哪里开始查看终端中的数据)。

感谢简单的回答(如果我更有经验,我不会发布这样的基本问题)。谢谢,

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

int main()
{

    // hardcode opening of card.raw in read binary mode
    FILE *infile = fopen("card.raw", "rb");

    if (infile == NULL)
    {
        fprintf(stderr, "Could not open infile"); 
        return 2;
    } 

    // declare a variable to hold data to be read from infile file, note that a size for it must be specified
    char text[32];

    /* go to the beginning of the card.raw file to start reading */
    fseek(infile, 0, SEEK_SET);

    // text is the variable that will hold what is read, declared above
    // how many to read, how many to read at a time, where to read from
    fread(text, 32, 1, infile);
    printf("%s\n", text);
}

【问题讨论】:

  • 欢迎提出基本问题,但每个问题只能发布一个问题。
  • 在十六进制转储中,左侧的数字是数据的偏移量,数据由中间的十六进制数据和右侧的这些十六进制值的 ascii 表示。 Hexdump 一个文本文件,你会看到它是如何工作的。
  • 您也可以在此处查找有关 CS50 的问题和答案。 cs50.stackexchange.com

标签: c cs50 recover


【解决方案1】:

有几个重大问题。首先声明char text[32];。回想一下char 有一个非常具体的含义,它被评估为从 0 到 255 的整数;它是“签名的”。这非常适合阅读 ascii 文本。从resize 调用/查看 bmp.h 以了解应如何声明数据以读取 ascii 文本的数据,例如图像数据。

-- 编辑 -- 二进制数据需要是“无符号”数据类型。在bmp.h中,作者在这里使用了uint8_ttypedef uint8_t BYTE;(需要#include stdint.h&gt;)。你可以使用
unsigned char text[32]

其次是printf("%s\n", text);text 被声明为一个字符数组。但是还记得使字符串成为字符串的东西吗?它是终止的空字节,技术上是0。因此,当您要求 printf 将 text 作为字符串打印时,它将打印直到第一个空字节 (0) 的所有内容。正如您从十六进制转储中看到的那样,它是文件中的第一个字节。

--edit-- 由于您不能在 printf 中使用字符串格式,因此您可以一次打印一个字符,就像 mario 或 caesar 一样。但是,由于它是无符号的,格式字符串将是 %u 而不是 %c。您可以使用格式字符串%04xx 是十六进制的说明符)以十六进制形式查看它。

【讨论】:

  • 谢谢,但您的提示仍然超出我的想象。我知道前 32 个字节是 0,只是不知道如何在 Card.raw 文件中的 C 或 python 中显示它们。我查看了 bmp.h 文件,但不完全理解我认为您指向我的 Byte、Dword、Long、Word 的区别。 (我并不真正关心前 32 个字节,我只想在屏幕上打印一些东西,这样我就可以看到我正在访问正确的数据)。
  • 我在答案中添加了更多具体信息。我希望它能让你走上正确的道路。
【解决方案2】:

感谢 DinoCoderSAurus,在您(和其他一些帮助)的帮助下,我能够弄清楚以下内容:

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

int main()
{

    // hardcode opening of a file with fopen, in read binary mode
    FILE *infile = fopen("card.raw", "rb");
    // error check, did file open?
    if (infile == NULL)
    {
        fprintf(stderr, "Could not open infile"); 
        return 2;
    }

    // because card.raw contains binary/hex data, must use unsigned char to hold data, 32 bytes chosen at random
    unsigned char dataval[32];

    //    dataval is the variable that will hold what is read, declared above
    //          how many to read, how many to read at a time, where to read from
    fread(dataval, 1, 32, infile);

    //Print bytes (from dataval) one at a time
    for (int i = 0; i < 32; i++)
    {
        printf("%02X ", (int)dataval[i]);
    }
    printf("\n");

    return 0;
}

【讨论】:

    猜你喜欢
    • 2018-07-22
    • 2020-09-04
    • 2020-12-02
    • 1970-01-01
    • 2019-09-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多