图像处理中各种边缘检测的微分算子简单比较(Sobel,Robert, Pre

各种算子的存在就是对这种导数分割原理进行的实例化计算,是为了在计算过程中直接使用的一种计算单位;

边缘检测算子是一种利用局部差分算子寻找边缘的算子

算子对边缘的定位不如Roberts算子。

算子和Prewitt算子都是加权平均,但是Sobel算子认为,邻域的像素对当前像素产生的影响不是等价的,所以距离不同的像素具有不同的权值,对算子结果产生的影响也不同。一般来说,距离越远,产生的影响越小。

算子是滤波算子的形式,用于提取边缘,可以利用快速卷积函数,简单有效,因此应用广泛。美中不足的是,Sobel算子并没有将图像的主体与背景严格地区分开来,换言之就是Sobel算子没有基于图像灰度进行处理,由于Sobel算子没有严格地模拟人的视觉生理特征,所以提取的图像轮廓有时并不能令人满意。在观测一幅图像的时候,我们往往首先注意的是图像与背景不同的部分,正是这个部分将主体突出显示,基于该理论,我们可以给出阈值化轮廓提取算法,该算法已在数学上证明当像素点满足正态分布时所求解是最优的。

上面的算子是利用一阶导数的信息,属于梯度算子范畴。

算子和平滑算子结合起来生成一个新的模板。

算子对噪声具有无法接受的敏感性;同时其幅值产生算边缘,这是复杂的分割不希望有的结果;最后Laplacian算子不能检测边缘的方向;所以Laplacian在分割中所起的作用包括:(1)利用它的零交叉性质进行边缘定位;(2)确定一个像素是在一条边缘暗的一面还是亮的一面;一般使用的是高斯型拉普拉斯算子(Laplacian of a Gaussian,LoG),由于二阶导数是线性运算,利用LoG卷积一幅图像与首先使用高斯型平滑函数卷积改图像,然后计算所得结果的拉普拉斯是一样的。所以在LoG公式中使用高斯函数的目的就是对图像进行平滑处理,使用Laplacian算子的目的是提供一幅用零交叉确定边缘位置的图像;图像的平滑处理减少了噪声的影响并且它的主要作用还是抵消由Laplacian算子的二阶导数引起的逐渐增加的噪声影响。

微分算子在图像处理中扮演重要的角色,其算法实现简单,而且边缘检测的效果又较好,因此这些基本的微分算子是学习图像处理过程中的必备方法,下面着重讨论几种常见的微分算子。

1.Sobel

其主要用于边缘检测,在技术上它是以离散型的差分算子,用来运算图像亮度函数的梯度的近似值,缺点是Sobel算子并没有将图像的主题与背景严格地区分开来,换言之就是Sobel算子并没有基于图像灰度进行处理,由于Sobel算子并没有严格地模拟人的视觉生理特征,所以提取的图像轮廓有时并不能令人满意,算法具体实现很简单,就是3*3的两个不同方向上的模板运算,这里不再写出。

2.Robert算子

根据任一相互垂直方向上的差分都用来估计梯度,Robert算子采用对角方向相邻像素只差

3.Prewitt算子

该算子与Sobel算子类似,只是权值有所变化,但两者实现起来功能还是有差距的,据经验得知Sobel要比Prewitt更能准确检测图像边缘。

4.Laplacian算子

拉普拉斯算子是一种二阶微分算子,若只考虑边缘点的位置而不考虑周围的灰度差时可用该算子进行检测。对于阶跃状边缘,其二阶导数在边缘点出现零交叉,并且边缘点两旁的像素的二阶导数异号。

5.Canny算子

该算子功能比前面几种都要好,但是它实现起来较为麻烦,Canny算子是一个具有滤波,增强,检测的多阶段的优化算子,在进行处理前,Canny算子先利用高斯平滑滤波器来平滑图像以除去噪声,Canny分割算法采用一阶偏导的有限差分来计算梯度幅值和方向,在处理过程中,Canny算子还将经过一个非极大值抑制的过程,最后Canny算子还采用两个阈值来连接边缘。

下面算法是基于的算法不可能直接运行,,只是我把Canny的具体实现步骤写了出来,若需用还要自己写。

该算子具体实现方法:

// anny.cpp: implementation of the Canny class.////////////////////////////////////////////////////////////////////////

#include “anny.h”#include “math.h”//#include “algorithms.h”//#include “algorithm.h”#include “stdlib.h”//#include “maths.h”//using namespace std;//////////////////////////////////////////////////////////////////////// Construction/Destruction//////////////////////////////////////////////////////////////////////

Canny::Canny(int PicHeight,int PicWidth,double ** PicData,double PicSigma,double PicRatioLow,double PicRatioHigh){iHeight=PicHeight;iWidth=PicWidth;iData=PicData;sigma=PicSigma;dRatioLow=PicRatioLow;dRatioHigh=PicRatioHigh;}

Canny::~Canny(){

}

void Canny::CannyArith(int **iEdgePoint){int i;int **iGradX ; // 指向x方向导数的指针 int **iGradY ; // 指向y方向导数的指针 int **iExtent ; // 梯度的幅度iGradX=new int *[iHeight];for(i=0;i<iHeight;i++)iGradX[i]=new int[iWidth];iGradY=new int *[iHeight];for(i=0;i<iHeight;i++)iGradY[i]=new int[iWidth];iExtent=new int *[iHeight];for(i=0;i<iHeight;i++)iExtent[i]=new int[iWidth];// 对原图象进行滤波 GaussionSmooth();//计算X,Y方向上的方向导数 DirGrad(iGradX,iGradY); // 计算梯度的幅度 GradExtent(iGradX,iGradY,iExtent); // 应用non-maximum 抑制 NonMaxSuppress(iExtent,iGradX,iGradY,iEdgePoint);// 应用Hysteresis,找到所有的边界 Hysteresis(iExtent,iEdgePoint);// 释放内存for(i=0;i<iHeight;i++) delete []*(iGradX+i); delete iGradX;for(i=0;i<iHeight;i++) delete []*(iGradY+i); delete iGradY;for(i=0;i<iHeight;i++) delete []*(iExtent+i); delete iExtent;}

一个背包,几本书,所有喜欢的歌,

图像处理中各种边缘检测的微分算子简单比较(Sobel,Robert, Pre

相关文章:

你感兴趣的文章:

标签云: