加载中…
个人资料
  • 博客等级:
  • 博客积分:
  • 博客访问:
  • 关注人气:
  • 获赠金笔:0支
  • 赠出金笔:0支
  • 荣誉徽章:
正文 字体大小:

图像处理之高斯一阶及二阶导数计算

(2016-03-26 01:10:42)
标签:

高斯

导数

图像

高斯导数算子

高斯求导

本质:图像×高斯函数的导数的mask(所谓算子)

以下为转载,看官有自己的看法和理解请留言。


图像处理之高斯一阶及二阶导数计算

 

图像的一阶与二阶导数计算在图像特征提取与边缘提取中十分重要。一阶与二阶导数的

作用,通常情况下:

一阶导数可以反应出图像灰度梯度的变化情况

二阶导数可以提取出图像的细节同时双响应图像梯度变化情况

常见的算子有Robot, Sobel算子,二阶常见多数为拉普拉斯算子,如图所示:

http://img.blog.csdn.net/20131117125855281

 

对于一个1D的有限集合数据f(x) = {1…N}, 假设dx的间隔为1则一阶导数计算公式如下:

Df(x) = f(x+1) – f(x-1) 二阶导数的计算公式为:df(x)= f(x+1) + f(x-1) – 2f(x);

稍微难一点的则是基于高斯的一阶导数与二阶导数求取,首先看一下高斯的1D与2D的

公式。一维高斯对应的X阶导数公式:

http://img.blog.csdn.net/20131117125946187

 

二维高斯对应的导数公式:

http://img.blog.csdn.net/20131117130148000

 

二:算法实现

1.      高斯采样,基于间隔1计算,计算mask窗口计算,这样就跟普通的卷积计算差不多

2.      设置sigma的值,本例默认为10,首先计算高斯窗口函数,默认为3 * 3

3.      根据2的结果,计算高斯导数窗口值

4.      卷积计算像素中心点值。

注意点计算高斯函数一定要以零为中心点, 如果窗口函数大小为3,则表达为-1, 0, 1

三:程序实现关键点

1.      归一化处理,由于高斯计算出来的窗口值非常的小,必须实现归一化处理。

2.      亮度提升,对X,Y的梯度计算结果进行了亮度提升,目的是让大家看得更清楚。

3.      支持一阶与二阶单一方向X,Y偏导数计算

四:运行效果:

高斯一阶导数X方向效果

http://img.blog.csdn.net/20131117130521750

高斯一阶导数Y方向效果

http://img.blog.csdn.net/20131117130608515

五:算法全部源代码:

[java] view plain copy
  1.   
  2. package com.gloomyfish.image.harris.corner;  
  3. import java.awt.image.BufferedImage;  
  4.   
  5. import com.gloomyfish.filter.study.AbstractBufferedImageOp;  
  6.   
  7. public class GaussianDerivativeFilter extends AbstractBufferedImageOp  
  8.   
  9.     public final static int X_DIRECTION 0 
  10.     public final static int Y_DIRECTION 16 
  11.     public final static int XY_DIRECTION 2 
  12.     public final static int XX_DIRECTION 4 
  13.     public final static int YY_DIRECTION 8 
  14.       
  15.     // private attribute and settings  
  16.     private int DIRECTION_TYPE 0 
  17.     private int GAUSSIAN_WIN_SIZE 1// N*2 1  
  18.     private double sigma 10// default  
  19.   
  20.     public GaussianDerivativeFilter()  
  21.      
  22.         System.out.println("高斯一阶及多阶导数滤镜");  
  23.         
  24.       
  25.     public int getGaussianWinSize()  
  26.         return GAUSSIAN_WIN_SIZE;  
  27.      
  28.   
  29.     public void setGaussianWinSize(int gAUSSIAN_WIN_SIZE)  
  30.         GAUSSIAN_WIN_SIZE gAUSSIAN_WIN_SIZE;  
  31.      
  32.     public int getDirectionType()  
  33.         return DIRECTION_TYPE;  
  34.      
  35.   
  36.     public void setDirectionType(int dIRECTION_TYPE)  
  37.         DIRECTION_TYPE dIRECTION_TYPE;  
  38.      
  39.   
  40.     @Override  
  41.     public BufferedImage filter(BufferedImage src, BufferedImage dest)  
  42.         int width src.getWidth();  
  43.         int height src.getHeight();  
  44.   
  45.         if dest == null  
  46.             dest createCompatibleDestImage( src, null );  
  47.   
  48.         int[] inPixels new int[width*height];  
  49.         int[] outPixels new int[width*height];  
  50.         getRGB( src, 00width, height, inPixels );  
  51.         int index 0index2 0 
  52.         double xred 0xgreen 0xblue 0 
  53.         // double yred 0, ygreen 0, yblue 0;  
  54.         int newRow, newCol;  
  55.         double[][] winDeviationData getDirectionData();  
  56.   
  57.         for(int row=0row
  58.             int ta 255tr 0tg 0tb 0 
  59.             for(int col=0col
  60.                 index row width col;  
  61.                 for(int subrow -GAUSSIAN_WIN_SIZE; subrow <= GAUSSIAN_WIN_SIZE; subrow++)  
  62.                     for(int subcol -GAUSSIAN_WIN_SIZE; subcol <= GAUSSIAN_WIN_SIZE; subcol++)  
  63.                         newRow row subrow;  
  64.                         newCol col subcol;  
  65.                         if(newRow 0 || newRow >= height)  
  66.                             newRow row;  
  67.                          
  68.                         if(newCol 0 || newCol >= width)  
  69.                             newCol col;  
  70.                          
  71.                         index2 newRow width newCol;  
  72.                         tr (inPixels[index2] >> 160xff 
  73.                         tg (inPixels[index2] >> 80xff 
  74.                         tb inPixels[index2] 0xff 
  75.                         xred += (winDeviationData[subrow GAUSSIAN_WIN_SIZE][subcol GAUSSIAN_WIN_SIZE] tr);  
  76.                         xgreen +=(winDeviationData[subrow GAUSSIAN_WIN_SIZE][subcol GAUSSIAN_WIN_SIZE] tg);  
  77.                         xblue +=(winDeviationData[subrow GAUSSIAN_WIN_SIZE][subcol GAUSSIAN_WIN_SIZE] tb);  
  78.                      
  79.                  
  80.                   
  81.                 outPixels[index] (ta << 24(clamp((int)xred) << 16(clamp((int)xgreen) << 8clamp((int)xblue);  
  82.                   
  83.                 // clean up values for next pixel  
  84.                 newRow newCol 0 
  85.                 xred xgreen xblue 0 
  86.                 // yred ygreen yblue 0;  
  87.              
  88.          
  89.   
  90.         setRGB( dest, 00width, height, outPixels );  
  91.         return dest;  
  92.      
  93.       
  94.     private double[][] getDirectionData()  
  95.      
  96.         double[][] winDeviationData null 
  97.         if(DIRECTION_TYPE == X_DIRECTION)  
  98.          
  99.             winDeviationData this.getXDirectionDeviation();  
  100.          
  101.         else if(DIRECTION_TYPE == Y_DIRECTION)  
  102.          
  103.             winDeviationData this.getYDirectionDeviation();  
  104.          
  105.         else if(DIRECTION_TYPE == XY_DIRECTION)  
  106.          
  107.             winDeviationData this.getXYDirectionDeviation();  
  108.          
  109.         else if(DIRECTION_TYPE == XX_DIRECTION)  
  110.          
  111.             winDeviationData this.getXXDirectionDeviation();  
  112.          
  113.         else if(DIRECTION_TYPE == YY_DIRECTION)  
  114.          
  115.             winDeviationData this.getYYDirectionDeviation();  
  116.          
  117.         return winDeviationData;  
  118.      
  119.       
  120.     public int clamp(int value)  
  121.         // trick, just improve the lightness otherwise image is too darker...  
  122.         if(DIRECTION_TYPE == X_DIRECTION || DIRECTION_TYPE == Y_DIRECTION)  
  123.          
  124.             value value 10 50 
  125.          
  126.         return value 0 0 (value 255 255 value);  
  127.      
  128.       
  129.     // centered on zero and with Gaussian standard deviation  
  130.     // parameter sigma  
  131.     public double[][] get2DGaussianData()  
  132.      
  133.         int size GAUSSIAN_WIN_SIZE 2 1 
  134.         double[][] winData new double[size][size];  
  135.         double sigma2 this.sigma sigma;  
  136.         for(int i=-GAUSSIAN_WIN_SIZE; i<=GAUSSIAN_WIN_SIZE; i++)  
  137.          
  138.             for(int j=-GAUSSIAN_WIN_SIZE; j<=GAUSSIAN_WIN_SIZE; j++)  
  139.              
  140.                 double i*1 j*j;  
  141.                 double sum -(r/(2*sigma2));  
  142.                 winData[i GAUSSIAN_WIN_SIZE][j GAUSSIAN_WIN_SIZE] Math.exp(sum);  
  143.              
  144.          
  145.         return winData;  
  146.      
  147.       
  148.     public double[][] getXDirectionDeviation()  
  149.      
  150.         int size GAUSSIAN_WIN_SIZE 2 1 
  151.         double[][] data get2DGaussianData();  
  152.         double[][] xDeviation new double[size][size];  
  153.         double sigma2 this.sigma sigma;  
  154.         for(int x=-GAUSSIAN_WIN_SIZE; x<=GAUSSIAN_WIN_SIZE; x++)  
  155.          
  156.             double -(x/sigma2);  
  157.             for(int i=0i
  158.              
  159.                 xDeviation[i][x GAUSSIAN_WIN_SIZE] data[i][x GAUSSIAN_WIN_SIZE];                
  160.              
  161.          
  162.         return xDeviation;  
  163.      
  164.       
  165.     public double[][] getYDirectionDeviation()  
  166.      
  167.         int size GAUSSIAN_WIN_SIZE 2 1 
  168.         double[][] data get2DGaussianData();  
  169.         double[][] yDeviation new double[size][size];  
  170.         double sigma2 this.sigma sigma;  
  171.         for(int y=-GAUSSIAN_WIN_SIZE; y<=GAUSSIAN_WIN_SIZE; y++)  
  172.          
  173.             double -(y/sigma2);  
  174.             for(int i=0i
  175.              
  176.                 yDeviation[y GAUSSIAN_WIN_SIZE][i] data[y GAUSSIAN_WIN_SIZE][i];                
  177.              
  178.          
  179.         return yDeviation;  
  180.      
  181.       
  182.       
  183.     public double[][] getXYDirectionDeviation()  
  184.      
  185.         int size GAUSSIAN_WIN_SIZE 2 1 
  186.         double[][] data get2DGaussianData();  
  187.         double[][] xyDeviation new double[size][size];  
  188.         double sigma2 sigma sigma;  
  189.         double sigma4 sigma2 sigma2;  
  190.         // TODO:zhigang  
  191.         for(int x=-GAUSSIAN_WIN_SIZE; x<=GAUSSIAN_WIN_SIZE; x++)  
  192.          
  193.             for(int y=-GAUSSIAN_WIN_SIZE; y<=GAUSSIAN_WIN_SIZE; y++)  
  194.              
  195.                 double -((x*y)/sigma4);  
  196.                 xyDeviation[x GAUSSIAN_WIN_SIZE][y GAUSSIAN_WIN_SIZE] data[x GAUSSIAN_WIN_SIZE][y GAUSSIAN_WIN_SIZE];  
  197.              
  198.          
  199.         return normalizeData(xyDeviation);  
  200.      
  201.       
  202.     private double[][] normalizeData(double[][] data)  
  203.      
  204.         // normalization the data  
  205.         double min data[0][0];  
  206.         for(int x=-GAUSSIAN_WIN_SIZE; x<=GAUSSIAN_WIN_SIZE; x++)  
  207.          
  208.             for(int y=-GAUSSIAN_WIN_SIZE; y<=GAUSSIAN_WIN_SIZE; y++)  
  209.              
  210.                 if(min data[x GAUSSIAN_WIN_SIZE][y GAUSSIAN_WIN_SIZE])  
  211.                  
  212.                     min data[x GAUSSIAN_WIN_SIZE][y GAUSSIAN_WIN_SIZE];  
  213.                  
  214.              
  215.          
  216.           
  217.         for(int x=-GAUSSIAN_WIN_SIZE; x<=GAUSSIAN_WIN_SIZE; x++)  
  218.          
  219.             for(int y=-GAUSSIAN_WIN_SIZE; y<=GAUSSIAN_WIN_SIZE; y++)  
  220.              
  221.                 data[x GAUSSIAN_WIN_SIZE][y GAUSSIAN_WIN_SIZE] data[x GAUSSIAN_WIN_SIZE][y GAUSSIAN_WIN_SIZE] /min;  
  222.              
  223.          
  224.           
  225.         return data;  
  226.      
  227.       
  228.     public double[][] getXXDirectionDeviation()  
  229.      
  230.         int size GAUSSIAN_WIN_SIZE 2 1 
  231.         double[][] data get2DGaussianData();  
  232.         double[][] xxDeviation new double[size][size];  
  233.         double sigma2 this.sigma sigma;  
  234.         double sigma4 sigma2 sigma2;  
  235.         for(int x=-GAUSSIAN_WIN_SIZE; x<=GAUSSIAN_WIN_SIZE; x++)  
  236.          
  237.             double -((x sigma2)/sigma4);  
  238.             for(int i=0i
  239.              
  240.                 xxDeviation[i][x GAUSSIAN_WIN_SIZE] data[i][x GAUSSIAN_WIN_SIZE];               
  241.              
  242.          
  243.         return xxDeviation;  
  244.      
  245.       
  246.     public double[][] getYYDirectionDeviation()  
  247.      
  248.         int size GAUSSIAN_WIN_SIZE 2 1 
  249.         double[][] data get2DGaussianData();  
  250.         double[][] yyDeviation new double[size][size];  
  251.         double sigma2 this.sigma sigma;  
  252.         double sigma4 sigma2 sigma2;  
  253.         for(int y=-GAUSSIAN_WIN_SIZE; y<=GAUSSIAN_WIN_SIZE; y++)  
  254.          
  255.             double -((y sigma2)/sigma4);  
  256.             for(int i=0i
  257.              
  258.                 yyDeviation[y GAUSSIAN_WIN_SIZE][i] data[y GAUSSIAN_WIN_SIZE][i];               
  259.              
  260.          
  261.         return yyDeviation;  
  262.      
  263.   
  264.  

部分转自:http://blog.csdn.net/jia20003/article/details/16369143

0

阅读 收藏 喜欢 打印举报/Report
  

新浪BLOG意见反馈留言板 欢迎批评指正

新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 产品答疑

新浪公司 版权所有