首页 文章

用C读取PGM图像

提问于
浏览
0

我正在尝试使用以下功能读取PGM图像:

typedef struct PGMImage{
    int w;
    int h;
    unsigned char* data;
}GrayImage;

    void ReadPGMImage(char* filename,GrayImage* image)
    {
        int width,height,size,binary,i,j;

        FILE  *fp = fopen(filename, "r");

        if(!fp){
           fprintf(stderr,"Unable to open file in 'r' mode");
           exit(errno);
        }

        readPNMHeader(fp, &width, &height,&binary);

        size = width * height;
        *image = CreateGrayImage(width,height);

        if (!(image->data)){
            fprintf(stderr,"Memory not allocated");
            exit(errno);
        }

        fread((void *)image->data, sizeof(unsigned char), (size_t) size, fp);

        fclose(fp);

        return;
    }

我试图读取的图像有这些 Headers :P2 640 480 255

当我打印出某些像素的值(行:400-410,列:300-310)时,将为所有像素打印“205”,而根据Matlab的实际值为:

>248  255  255  250  254  254  254  252  252  255
  >255  255  255  255  255  255  255  255  255  255
  >255  255  255  255  255  255  255  255  255  255
  >255  255  255  255  255  255  255  255  255  255
  >255  255  255  255  255  255  255  255  255  255
  >248  247  249  245  251  252  253  252  245  251
  >241  240  243  237  240  244  239  242  243  244
  >235  238  238  237  239  238  239  238  240  242
  >236  233  241  235  236  234  236  239  235  237
  >231  239  231  239  234  234  230  233  233  234

当我读取PPM图像时,类似的代码也有效 . 有人能告诉我哪里出错了吗?

编辑:有效的最终代码:

void ReadPGMImage(char * fileName, GrayImage* image) {
    FILE * fp = NULL;
    char version[100];
    int levels = 0;
    unsigned int w = 0, h = 0;
    unsigned int i = 0;
    int pixdat = 0;



    if( fileName == NULL ) {
        fprintf(stderr,"Bad file name=%s\n", fileName );
        return;
    }

    fp = fopen(fileName,"rb");
    if( fp == NULL )    {
        fprintf(stderr,"Cannot open file = %s\n", fileName );
        return;
    }


    fscanf(fp,"%s",version);

    SkipComments(fp);
    fscanf(fp, "%d", &w);
    SkipComments(fp);
    fscanf(fp, "%d", &h);
    SkipComments(fp);
    fscanf(fp, "%d", &levels);

    CreateGrayImage(image,w,h);
    image->w = w;
    image->h = h;
    for(i=0;i<w*h;i++) {
        fscanf(fp, "%d", &pixdat);
        image->data[i] = pixdat;
    }

    fclose(fp);

    return;
}

2 回答

  • 1

    到目前为止,代码似乎没有问题 .

    我认为以下代码行是导致问题的原因

    *image = CreateGrayImage(width,height);
    

    在这里,您将CreateGrayImage()返回的指针分配给* image,它会覆盖结构的内容 .

    我假设你想将CreateGrayImage()返回的指针传递给CreateGrayImage()的调用者 . 在这种情况下,您需要将ReadPGMImage()的函数声明更改为以下内容:

    void ReadPGMImage(char* filename,GrayImage** image)
    

    然后它应该按预期工作 .

  • 0

    PGM具有数据值的十进制表示,因此使用fscanf读取以下值:

    int offset=0;
    while(! feof(fp) ){
        fscanf(fp, "%hu", &value);
        image->data[offset++] = value;
    }
    

    %hu为您提供无符号短值(即0..65535值),因为PGM值可以是短路也可以是字节 . 在此基础上,为数据分配内存时,请确保使用:

    x->data = (unsigned short*)malloc( width * height * sizeof(unsigned short))
    

相关问题