Harris角点检测算法基本理解

HARRIS 定义的角点位于图像二阶导数的自相关矩阵有两个最大特征值的地方,所以采用二阶导数。

算法流程:

1. 对每个像素点计算图像在X方向Y方向的二阶偏导数,计算图像的XY方向的导数

首先计算Ix,Iy采用Sobel 算子计算近似一阶导数,在边缘检测中,常用的一种模板是Sobel 算子。Sobel 算子有两个,一个是检测水平边缘的 ;另一个是检测垂直边缘的 。公式如下:


求出Ix,Iy

部分代码如下:

//

定义水平方向差分算子并求

Ix 

    double dx[9]={-1,0,1,-1,0,1,-1,0,1}; 

mat_Ix=mbys(mat_I,cxDIB,cyDIB,dx,3,3); //

Ix

矩阵

//

定义水平方向差分算子并求

Ix 

    double dx[9]={-1,0,1,-1,0,1,-1,0,1}; 

mat_Ix=mbys(mat_I,cxDIB,cyDIB,dx,3,3); //

Ix

矩阵

</pre><div><pre name="code" class="html" style="color: rgb(51, 51, 51); font-size: 24px; line-height: 24px; text-indent: 28px;"> //定义水平方向差分算子并求Ix     
double dx[9]={-1,0,1,-2,0,2,-1,0,1}; 
mat_Ix=mbys(mat_I,cxDIB,cyDIB,dx,3,3); //求Ix矩阵

</pre><br style="color: rgb(51, 51, 51); font-family: arial, 宋体, sans-serif; font-size: 24px; line-height: 24px; text-indent: 28px;" /><div style="color: rgb(51, 51, 51); font-family: arial, 宋体, sans-serif; font-size: 24px; line-height: 24px; text-indent: 28px;"></div><div style="color: rgb(51, 51, 51); font-family: arial, 宋体, sans-serif; font-size: 24px; line-height: 24px; text-indent: 28px;"><pre name="code" class="html">CvMat *mbys(CvMat *mat,intxwidth,intywidth,double *a,int size1,int size2)//size  { inti,j; int i1,j1; intpx,py; int m; CvMat *mat1; 
    mat1=cvCloneMat(mat); 
for(i=size1/2;i<ywidth-size1/2;i++) for(j=size2/2;j<xwidth-size2/2;j++)         {             m=0; for(i1=0;i1<size1;i1++) for(j1=0;j1<size2;j1++)                 { px=i-size1/2+i1; py=j-size2/2+j1; 
                    //CV_MAT_ELEM访问矩阵元素 
                    m+=CV_MAT_ELEM(*mat,double,px,py)*a[i1*size1+j1];                             } 
                CV_MAT_ELEM(*mat1,double,i,j)=m;         } return mat1; }


其中同理得出IY

Ixx=IX*Ix;

Iyy=Iy*Iy;

Ixy=Ix*IY;

Ix表示x方向的一阶导数

其中Iy表示y方向的一阶导数

其中Ixx表示X方向的二阶偏导数

Iyy表示Y方向的二阶偏导数

Ixy表XY方向的二阶导数

2.对Ix2/Iy2/Ixy进行高斯平滑,以去除噪声


3.根据下列公式计算角点量(个人理解就是计算每个点的自相关矩阵的特征值)

下为自相关矩阵


计算角点量

 

计算角点量

 

角点量公式为

Ix2*Iy2-Ixy*IXY/IX+Iy;

4计算出角点量之后进行局部非极大值抑制

//用来求得局部极大值 
CvMat *mblocmax(CvMat *mat1,int xwidth,intywidth,int size) { inti,j; 
double max=-1000; int i1,j1; intpx,py; CvMat *mat; 
mat=cvCloneMat(mat1); 
for(i=size/2;i<ywidth-size/2;i++) for(j=size/2;j<xwidth-size/2;j++)         { max=-10000; 
for(i1=0;i1<size;i1++) 




 var cpro_psid ="u2572954"; var cpro_pswidth =966; var cpro_psheight =120;







for(j1=0;j1<size;j1++)                 { px=i-size/2+i1; py=j-size/2+j1; 
if(CV_MAT_ELEM(*mat1,double,px,py)>max) max=CV_MAT_ELEM(*mat1,double,px,py);  
                } if(max>0) 
                    CV_MAT_ELEM(*mat,double,i,j)=max; else 
                    CV_MAT_ELEM(*mat,double,i,j)=0;         } return mat; } 
//用来确认角点 
CvMat *mbcorner(CvMat *mat1,CvMat *mat2,int xwidth,intywidth,intsize,double thresh) { 
CvMat *mat; inti,j; 
mat=cvCreateMat(ywidth,xwidth,CV_32FC1); for(i=size/2;i<ywidth-size/2;i++) for(j=size/2;j<xwidth-size/2;j++)         { 
            if(CV_MAT_ELEM(*mat1,double,i,j)==CV_MAT_ELEM(*mat2,double,i,j))//首先取得局部极大值 //mat1是CRF相应的所有。Mat2是CRF局部极大值点.   
                if(CV_MAT_ELEM(*mat1,double,i,j)>thresh)//然后大于这个阈值                     CV_MAT_ELEM(*mat,int,i,j)=255;//满足上两个条件,才是角点! else 
                CV_MAT_ELEM(*mat,int,i,j)=0;         } return mat; }
最终获得角点

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值