Свертка для фильтрации изображений - PullRequest
0 голосов
/ 06 октября 2019

Я пытаюсь создать программу на C, которая применяет фильтр Гаусса к изображению. Я успешно создал функции для чтения / записи изображения с помощью libpng и функцию, которая создает ядро, связанное с гауссовой функцией.

Мой код вдохновлен этим: http://zarb.org/~gc/html/libpng.html, и он работалдля основных задач. Например, я мог бы увеличить значение красного и сохранить изображение. Проблема в том, что когда я пытаюсь применить матрицу свертки, у меня возникает ошибка сегментации, когда я пытаюсь получить доступ к значению указателя ptr. Я не понимаю, почему раньше я мог прочитать это значение, а не сейчас. Также как раз перед printf с gdb я могу прочитать значения, связанные с ptr. Здесь segfault с gdb:

0x0000555555555991 in convolute (image=0x7fffffffda80, matrice=0x7fffffffda78) at imageTools.c:157
157               printf("%d",ptr[0]);

Мне также интересно, является ли создание циклов, которые вычисляют значение для каждого пикселя, очень эффективным, потому что оно делает много вычислений, и я думаю, что это занимает много временив то время как в таких программах, как Photoshop, это почти мгновенно.

Вот мой код: imageTools.c

void convolute(image_t* image, double** matrice){
  image_t imageTemp = *image;
  int x,y,i,j;
  png_byte r,v,b;
  for(x=2;x<image->height-2;x++){
    for(y=2;y<image->width-2;y++){
      png_byte* new_row = imageTemp.row_pointers[x];
      png_byte* new_ptr = &(new_row[y*4]);
      /*png_byte* new_pixel = malloc(4*sizeof(png_byte));*/
      r=0;v=0;b=0;
      for(i=-2;i<3;i++){
        png_byte* row = image->row_pointers[i];
        for(j=-2;j<3;j++){
          png_byte* ptr = &(row[j*4]);
          printf("%d",ptr[0]); /* Here is the segfault*/
          r += (png_byte) ptr[0];
          v += (png_byte) ptr[1];
          b += (png_byte) ptr[2];
        }
      }
      printf("R: %d, V: %d, B: %d",r,v,b);
      new_ptr[0] = r;
      new_ptr[1] = v;
      new_ptr[2] = b;
    }
  }
  image = &imageTemp;
}

main.c

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

#define PNG_DEBUG 3
#include <png.h>

#include "imageTools.h"
#include "filtreGaussien.h"

int main()
{
    image_t image;
    double** noyau;
    int i,j;

    if(read_png_file("test.png", &image)){
      printf("OK!\n");
      printf("Height: %d, Width: %d\n", image.height, image.width);

      noyau  = noyauGaussien(1.0);
      for(i=0;i<5;i++){
        printf("| ");
        for(j=0;j<5;j++){
          printf("%f | ",noyau[i][j]);
        }
        printf("\n");
      }

      convolute(&image, &noyau);

      write_png_file("test2.png", &image);
    } else {
      printf("An error as occured. Exiting...");
    }
    return 0;
}

image_t структура:

typedef struct{
  png_bytep* row_pointers;
  int width;
  int height;
  png_byte color_type;
  png_byte bit_depth;
}
image_t;
...