【发布时间】:2018-07-08 18:30:34
【问题描述】:
我正在尝试编写一个使用 C 将 p3 PPM 文件转换为 P6 的程序。但我遇到了两个问题。 1,我的代码出现分段错误。和 2,标头没有被正确读入转换后的 p6 文件。这是我的头文件。
#ifndef PPM_UTILS
#define PPM_UTILS
#include "stdio.h"
#include "stdlib.h"
#include "string.h"
// First meaningful line of the PPM file
typedef struct header {
char MAGIC_NUMBER[3];
unsigned int HEIGHT, WIDTH, MAX_COLOR;
} header_t;
// Represents an RGB pixel with integer values between 0-255
typedef struct pixel {
unsigned int R, G, B;
} pixel_t;
// PPM Image representation
typedef struct image {
header_t header;
pixel_t* pixels;
} image_t;
header_t read_header(FILE* image_file);
image_t* read_ppm(FILE* image_file);
image_t* read_p6(FILE* image_file, header_t header);
image_t* read_p3(FILE* image_file, header_t header);
void write_header(FILE* out_file, header_t header);
void write_p6(FILE* out_file, image_t* image);
void write_p3(FILE* out_file, image_t* image);
#endif
我将代码的主要部分拆分为我在编译器中合并的两个文件
#include <stdio.h>
#include "ppm_utils.h"
header_t read_header(FILE* image_file)
{
header_t header;
fscanf(image_file, "%c %d %d %d",header.MAGIC_NUMBER, &header.WIDTH, &header.HEIGHT, &header.MAX_COLOR);
return header;
}
void write_header(FILE* out_file, header_t header)
{
fprintf(out_file, "%c %d %d %d", *header.MAGIC_NUMBER,header.HEIGHT,header.WIDTH,header.MAX_COLOR);
}
image_t* read_ppm(FILE* image_file)
{
header_t header = read_header(image_file);
image_t* image = NULL;
if (strcmp("P3", header.MAGIC_NUMBER) == 0)
{
image = read_p3(image_file, header);
}
else if (strcmp("P6", header.MAGIC_NUMBER) == 0)
{
image = read_p6(image_file, header);
}
return image;
}
image_t* read_p6(FILE* image_file, header_t header)
{
int size;
size = header.HEIGHT * header.WIDTH;
image_t* image = (image_t*) malloc (sizeof(image_t));
image -> header = header;
image -> pixels = (pixel_t*) malloc (sizeof(pixel_t)* size);
char r,g,b;
r = 0;
g = 0;
b = 0;
int i;
for (i=0;i<size;i++){
fscanf(image_file, "%c%c%c", &r, &g, &b);
image -> pixels -> R = (int) r;
image -> pixels -> G = (int) g;
image -> pixels -> B = (int) b;
}
return image;
}
image_t* read_p3(FILE* image_file, header_t header)
{
int size;
size = header.HEIGHT * header.WIDTH;
image_t* image = (image_t*) malloc (sizeof(image_t));
image -> header = header;
image -> pixels = (pixel_t*) malloc (sizeof(pixel_t)* size);
int r,g,b;
r = 0;
g = 0;
b = 0;
int i;
for (i=0;i<size;i++){
fscanf(image_file, "%d %d %d ", &r, &g, &b);
image -> pixels -> R = (int) r;
image -> pixels -> G = (int) g;
image -> pixels -> B = (int) b;
}
return image;
}
void write_p6(FILE* out_file, image_t* image)
{
header_t header = image -> header;
header.MAGIC_NUMBER[1]=6;
write_header(out_file, header);
int size = header.HEIGHT * header.WIDTH;
int i;
for (i=0;i<size;i++){
fprintf(out_file,"%c%c%c", (char) image->pixels->R, (char) image->pixels->G, (char) image->pixels->B);
}
}
void write_p3(FILE* out_file, image_t* image)
{
header_t header = image -> header;
header.MAGIC_NUMBER[1]=3;
write_header(out_file, header);
int size = header.HEIGHT * header.WIDTH;
int i;
for (i=0;i<size;i++){
fprintf(out_file,"%d %d %d ",image->pixels->R,image->pixels->G,image->pixels->B);
}
}
..
#include <stdio.h>
#include "ppm_utils.h"
int main(int argc, char *argv[])
{
if (argc != 3)
{
printf("The program needs two arguments");
return 1;
}
FILE *fr;
fr = fopen(argv[1],"r");
if (fr == NULL)
{
printf("The opening failed");
}
FILE *fw;
fw = fopen(argv[2],"w");
if (fw == NULL)
{
printf("The opening failed");
}
image_t* image = read_ppm(fr);
write_p6(fw,image);
free(image);
free(image->pixels);
fclose(fr);
fclose(fw);
return 0;
}
你们有什么解决办法吗?
【问题讨论】:
-
你得到了分段错误,因为你首先释放了一个结构(图像),然后尝试访问/释放一个成员(图像->像素)
-
我注意到了一件事。在您的头文件中,您在引号中包含标准库头(
"stdio.h"等),而不是尖括号(<stdio.h>)。引号仅适用于这些标题与您的标题位于同一目录中的情况。
标签: c pointers segmentation-fault ppm