CS50 pset4恢复-仅在生成7168个jpeg后循环进入循环

时间:2020-10-16 13:30:51

标签: c cs50

因此,我正在执行CS50 pset4恢复任务(您需要在存储卡上搜索jpg文件,无论何时找到一个,您都要打开一个新文件并将找到的jpg写入新文件)。由于某种原因,第31行上的fread循环中的while一直持续到生成7168张图像为止(应该只有50张)。我的理解是,当fread到达文件末尾时,它将停止返回已读取的项目数。作为参考,可以在这里找到完整的任务描述:https://cs50.harvard.edu/x/2020/psets/4/recover/

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

typedef uint8_t  BYTE;

int main(int argc, char *argv[])
{
    if (argc != 2)
    {
        printf("Usage: recover [filename]\n");
        return 1;
    }

    char *filename = argv[1];

    FILE *file = fopen(argv[1], "r");
    if (file == NULL)
    {
        fprintf(stderr, "Could not open %s.\n", filename);
        return 2;
    }

    BYTE buffer[512];
    int counter = 0;
    char *imagename = malloc(sizeof(char)*12);
    FILE *img = NULL;

    while (fread(&buffer, 512, 1, file) == 1)
    {
        if (counter > 50) // added to break while loop after 50 jpegs have been generated
        {
            break;
        }

        if (buffer[0] == 0xff && buffer[1] == 0xd8 && buffer[2] == 0xff && (buffer[3] & 0xf0) == 0xe0)
        {
            if (counter > 0)
            {
                fclose(img);
            }
            sprintf(imagename, "%03i.jpg", counter);
            img = fopen(imagename, "w");
            if (img == NULL)
            {
                fclose(file);
                fprintf(stderr, "Could not create %s.\n", imagename);
                return 3;
            }
            fwrite(&buffer, 512, 1, img);
            counter++;
        }
        else
        {
            if (counter > 0)
            {
                fwrite(&buffer, 512, 1, img);
            }
        }
    }

    fclose(img);
    free(imagename);
    fclose(file);
    return 0;
}

2 个答案:

答案 0 :(得分:0)

以下建议的代码:

  1. 干净地编译
  2. 不包括未使用的头文件
  3. 执行所需的功能
  4. 兑现右边距(第72或80列)

现在,建议的代码:

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



int main(int argc, char *argv[])
{
    if (argc != 2)
    {
        fprintf( stderr, "Usage: %s [filename]\n", argv[0] );
        exit( EXIT_FAILURE );
    }

    FILE *fpin = fopen(argv[1], "r");
    if ( ! fpin )
    {
        perror( "fopen for input file failed" );
        exit( EXIT_FAILURE );
    }

    unsigned char buffer[512];
    int counter = 0;
    char imagename[12];
    
    FILE *fpout = NULL;

    while (fread(&buffer, 512, 1, fpin) == 1)
    {
        if(   buffer[0] == 0xff 
           && buffer[1] == 0xd8 
           && buffer[2] == 0xff 
           && (buffer[3] & 0xf0) == 0xe0)
        {
            if (counter > 0)
            {
                fclose( fpout );
            }
            
            sprintf(imagename, "%03i.jpg", counter);
            fpout = fopen(imagename, "w");
            if ( ! fpout )
            {
                perror( "fopen for write of individual image file failed" );
                fclose( fpin );
                exit( EXIT_FAILURE );
            }

            counter++;
        }
        
        size_t success = fwrite( buffer, 512, 1, fpout );
        if( ! success )
        {
            perror( "write of individual image record failed" );
            fclose(fpin);
            fclose(fpout);
            exit( EXIT_FAILURE );
        }
    }

    fclose(fpin);
    fclose(fpout);
    return 0;
}

答案 1 :(得分:-1)

不确定CS50 pset4恢复任务,但逻辑上我有以下评论:

为什么不在counter部分增加else变量?

让我们说您的条件if (buffer[0] == 0xff && buffer[1] == 0xd8 && buffer[2] == 0xff && (buffer[3] & 0xf0) == 0xe0)对于某些图像为true,然后您的counter变量将递增,之后,对于所有要在{{1 }}部分,无论任何情况,这都会增加图像数量,而不会增加计数。