C代码的指针

The pointer of C code

//
//  main.c
//  cbp
//
//  Created by Zhan on 16/4/13.
//  Copyright © 2016年 Zhan. All rights reserved.
//
#include <stdio.h>
#include <stdlib.h>
#include<math.h>

#pragma pack(2)

typedef unsigned short int WORD;
typedef unsigned int DWORD;

typedef struct BMP_FILE_HEADER
{
    WORD bType;
    DWORD bSize;
    WORD bReserved1;
    WORD bReserved2;
    DWORD bOffset;
} BMPFILEHEADER;

typedef struct BMP_INFO
{
    DWORD bInfoSize;
    DWORD bWidth;
    DWORD bHeight;
    WORD bPlanes;
    WORD bBitCount;
    DWORD bCompression;
    DWORD bmpImageSize;
    DWORD bXPelsPerMeter;
    DWORD bYPelsPerMeter;
    DWORD bClrUsed;
    DWORD bClrImportant;
} BMPINF;

/*彩色表*/
typedef struct RGB_QUAD
{
    WORD rgbBlue;
    WORD rgbGreen;
    WORD rgbRed;
    WORD rgbReversed;
} RGBQUAD;

int main()
{
    FILE *fp,*fpout;
    BMPFILEHEADER fileHeader;
    BMPINF infoHeader;
    int width, height;
    //WORD c;
    int s;
    float s1,s2;
    unsigned char **image;

    if((fp = fopen("XG.bmp", "rb")) == NULL)
    {
        printf("Cann't open the file!\n");
    }


    fseek(fp, 0, 0);
    fread(&fileHeader, sizeof(fileHeader), 1, fp);
    fread(&infoHeader, sizeof(infoHeader), 1, fp);

    printf("size fileHeader == %ld\n",sizeof(fileHeader));
    printf("size infoHader == %ld\n",sizeof(infoHeader));

    width = infoHeader.bWidth;
    height = abs(infoHeader.bHeight);

    printf("infoHeader.bWidth == %d\n",width);
    printf("infoHeader.bheight == %d\n",height);

    image = (unsigned char **)malloc(sizeof(unsigned char  *) * width);
    image[0] = (unsigned char *)malloc(sizeof(unsigned char ) * width * height);

    //    unsigned char **image1 =(unsigned char**) malloc (width*sizeof(int*));
    //    for(int i=0;i<width;i++)
    //        *image1++=(unsigned char*) malloc (height*sizeof(int));

    fseek(fp,(sizeof(fileHeader)+sizeof(infoHeader)),SEEK_SET);
    for(int i=0;i<width;i++)
    {
        for(int j=0;j<height;j++){
            fread(&image[i][j],1,1,fp); }}      //Memory leak ?
    for(int i=1;i<width;i++){
        for(int j=1;j<height;j++)
        {
            s1=image[i-1][j+1]+2*image[i][j+1]+image[i+1][j+1];
            s1=s1-image[i-1][j-1]-2*image[i][j-1]-image[i+1][j-1];
            s2=image[i-1][j-1]+2*image[i-1][j]+image[i-1][j+1];
            s2=s2-image[i+1][j-1]-2*image[i+1][j]-image[i+1][j+1];
            s=fabs(s1)+fabs(s2);
            if(s>80)
                image[i][j]=255;
            else
                image[i][j]=0;
        }
    }
    if((fpout=fopen("za.bmp","wb"))==NULL){
        printf("cannot open outfile!\n");
        free(image[0]);
        free(image);
        return 0;
    }
    printf("intoWrite\n");
    fwrite(&fileHeader,sizeof(fileHeader),1,fpout);
    fwrite(&infoHeader,sizeof(infoHeader),1,fpout);
    for(int i=0;i<width;i++)
    {
        for(int j=0;j<height;j++){
            printf("forWrite\n");
            fwrite(&image[i][j],1,1,fpout);}}
    //    c = fgetc(fp);
    //    int mi=0,mj=0;
    //    while (!feof(fp))
    //    {
    //        fwrite(&c,1,1,fpout);
    //        mi++;mj++;
    //    c = fgetc(fp);
    //    }
    free(image[0]);
    free(image);
    printf("OK!\n");
    fclose(fp);
    fclose(fpout);
    return 0;
}

这是我的bmp边缘代码detection.I使用Xcode到运行这段代码,它总是在[=15提示"Thread 1:EXC_BAD_ACCESS(code=1,address = 0x0)"或"Function call argument is an uninitialized value" =].为什么我用静态二维数组没有错误,但是动态二维数组有错误?

这将为每个 width 分配 height,您现在应该可以引用 image[i][j]

int each = 0;
image = malloc(sizeof(unsigned char  *) * width);
for ( each = 0; each < width; each++) {
    image[each] = malloc(sizeof(unsigned char ) * height);
}

释放将是相似的。

for ( each = 0; each < width; each++) {
    free ( image[each]);
}
free ( image);
image[0] = (unsigned char *)malloc(sizeof(unsigned char ) * width * height);

您只为一个数组分配空间,而不是整个查找 table,其中每个指针都指向分配的数组。

但是绝对没有必要首先在这里使用一些晦涩的查找 table。相反,使用二维数组:

width = ...;
height = ....;
unsigned char (*image)[][height];
image = malloc( sizeof(unsigned char[width][height]) );

...

free(image);

现在,因为你有一个真正的二维数组而不是一些零散的东西,如果你愿意,你可以一次读取整个数组:

fread(image, sizeof(unsigned[width][height]), 1, fp);

意思是:进入我的二维数组,从fp读取一个二维数组。您可以跳过循环。

image=(WORD **)calloc(width,sizeof(WORD*));
        if (NULL==image) return 1;
            for (a=0;a<width;a++) {
                image[a]=(WORD*)calloc(height,sizeof(WORD));
                if (NULL==image[a]){
                    printf("free image\n");
                    free(image);
                    return 2;}
            }

我用了calloc函数,这个函数就是分配内存和初始化。