2016-06-03 2 views
1

Мой выход оператора обнаружения края Sobel является странным. Вот мой код:Выход оператора обнаружения края Sobel Weird

BufferedImage temp = img; 
    float kernelx[][] = {{-1, 0, 1},{-2, 0, 2},{-1, 0, 1}}; 
    float kernely[][] = {{-1, -2, -1},{0, 0, 0},{1, 2, 1}}; 
    float valx = 0; 
    float valy = 0; 
    float val = 0; 
     for(int i=1;i<width-2;i++) { 
      for(int j=1;j<height-2;j++) { 
       valx = (kernelx[0][0]*new Color(img.getRGB(i-1, j-1)).getRed()) + (kernelx[0][2]*new Color(img.getRGB(i+1, j-1)).getRed()) + 
        (kernelx[1][0]*new Color(img.getRGB(i-1, j)).getRed()) + (kernelx[1][2]*new Color(img.getRGB(i+1, j)).getRed()) + 
        (kernelx[2][0]*new Color(img.getRGB(i-1, j+1)).getRed()) + (kernelx[2][2]*new Color(img.getRGB(i+1, j+1)).getRed()); 

       valy = (kernely[0][0]*new Color(img.getRGB(i-1, j-1)).getRed()) + (kernely[0][1]*new Color(img.getRGB(i, j-1)).getRed()) + (kernely[0][2]*new Color(img.getRGB(i+1, j-1)).getRed()) + 
         (kernely[2][0]*new Color(img.getRGB(i-1, j+1)).getRed()) + (kernely[2][1]*new Color(img.getRGB(i, j+1)).getRed()) + (kernely[2][2]*new Color(img.getRGB(i+1, j+1)).getRed()); 

       val = (float)sqrt(valx*valx+valy*valy); 

       val = val/1443*255; 
       if(val <= 127) { 
        val = 0; 
       } else { 
        val = 255; 
       } 
       temp.setRGB(i, j, new Color((int)val,(int)val,(int)val).getRGB()); 
      } 
      File outputfile = new File("src/image/edge.png"); 
      ImageIO.write(temp, "png", outputfile); 
     } 

Ничего плохого о моем коде? Пожалуйста, помогите мне. И вот картина результата.

Исходное изображение:

Original Image

Результат Изображение:

Resulted Image

ответ

2

Существуют различные проблемы в вашем коде:

  • При использовании ядра с размерами 3x3 вы переходите от [1,1] до] width-1, height-1 [, not] width-2, height-2 [.
  • В java используйте image.getRaster(). GetSample (x, y, channel) вместо нового цвета (img.getRGB (i-1, j-1)). GetRed()) '. Это будет намного быстрее и понятнее. То же самое при написании image.getRaster().setSample(x, y, channel, value)
  • При вычислении градиента Sobel на изображении, закодированном на [0, max], каждое направление (X и Y) будет давать вам значения на [-4 * max, 4 * max]. Поэтому агрессивно сокращать превышенные значения. Вместо этого вы можете выполнить растягивание гистограммы, тогда вы будете хранить гораздо больше информации.
  • Нормализация val = val/1443*255; зависит от вас, но не обязательно.
  • И, наконец, Основная проблема в ваш код. Полученное изображение (или temp в вашем случае) и исходное изображение ДОЛЖНЫ быть разными. Кроме того, вы модифицируете изображение одновременно с его обработкой. Это объясняет, почему у вас есть эта огромная белая область.
+0

А я вижу, спасибо за ответ, позвольте мне исправить мой код, и я дам вам знать результат. – Dennis

+0

Просто забудьте о третьем пункте, вы можете это сделать после. – FiReTiTi

+0

OMG .. это работает .. Большое спасибо :) – Dennis

Смежные вопросы