备注:源代码还未理解,所以未附上——下周任务

一、SIFT算法

1.算法简介

尺度不变特征转换即SIFT (Scale-invariant feature transform)是一种计算机视觉的算法。它用来侦测与描述影像中的局部性特征,它在空间尺度中寻找极值点,并提取出其位置、尺度、旋转不变量,此算法由 David Lowe在1999年所发表,2004年完善总结。
局部影像特征的描述与侦测可以帮助辨识物体,SIFT特征是基于物体上的一些局部外观的兴趣点而与影像的大小和旋转无关。对于光线、噪声、些微视角改变的容忍度也相当高。基于这些特性,它们是高度显著而且相对容易撷取,在母数庞大的特征数据库中,很容易辨识物体而且鲜有误认。使用 SIFT特征描述对于部分物体遮蔽的侦测率也相当高,甚至只需要3个以上的SIFT物体特征就足以计算出位置与方位。在现今的电脑硬件速度下和小型的特征数据库条件下,辨识速度可接近即时运算。SIFT特征的信息量大,适合在海量数据库中快速准确匹配。
 SIFT算法的实质是在不同的尺度空间上查找关键点(特征点),并计算出关键点的方向。SIFT所查找到的关键点是一些十分突出,不会因光照,仿射变换和噪音等因素而变化的点,如角点、边缘点、暗区的亮点及亮区的暗点等。

1.1哪些是SIFT要查找的关键点

1.2什么是尺度空间


2.算法流程

二、SIFT算法操作步骤

1.图像金字塔

1.1高斯金字塔

图像高斯金字塔(Gaussian Pyramid)是采用高斯函数对图像进行模糊以及降采样处理得到。其形成过程可如下图所示:

其中高斯模糊系数计算公式如下:

sigma0为基准层尺度(图像的初始尺度),o为组坐标(组数的索引值),r为每组层数的索引值,s为寻找极值点的尺度空间的组数,默认值为3(Lowe推荐为3)

1.1.1高斯函数与图像卷积

根据3σ原则,使用NxN的模板在图像每一个像素点处操作,其中N=[(6σ+1)]且向上取最邻近奇数。

其操作如下图:

1.1.2分离高斯卷积

上面这样直接与图像卷积,速度比较慢,同时图像边缘信息也会损失严重。后来,后来,不知哪位学者发现,可以使用分离的高斯卷积(即先用1xN的模板沿着X方向对图像卷积一次,然后用Nx1的模板沿着Y方向对图像再卷积一次,其中N=[(6σ+1)]且向上取最邻近奇数),这样既省时也减小了直接卷积对图像边缘信息的严重损失。

1.1.3高斯金字塔源码分析

1.2高斯差分金字塔

2002年Mikolajczyk在详细的实验比较中发现尺度归一化的高斯拉普拉斯函数的极大值和极小值同其它的特征提取函数,例如:梯度,Hessian或Harris角特征比较,能够产生最稳定的图像特征。而Lindeberg早在1994年就发现高斯差分函数(简称DOG算子)与尺度归一化的高斯拉普拉斯函数非常近似。如下式:

其中k-1是个常数,并不影响极值点位置的求取。

证明:

高斯模糊是一种图像滤波器,它使用正态分布(高斯函数)计算模糊模板,并使用该模板与原图像做卷积运算,达到模糊图像的目的。

N维空间正态分布方程为:

其中,是正态分布的标准差,值越大,图像越模糊(平滑)。r为模糊半径,模糊半径是指模板元素到模板中心的距离。如二维模板大小为m*n,则模板上的元素(x,y)对应的高斯计算公式为:

m,n表示高斯模板的维度(由确定)。(x, y)代表图像的像素位置。是尺度空间因子,值越小表示图像被平滑的越少,相应的尺度也就越小。大尺度对应于图像的概貌特征,小尺度对应于图像的细节特征。

为简单化,m,n取为0。

LOG算子如下:

可以看出:

由导数定义:

右边比LOG算子只是多了一个系数,在实际应用中不影响。

我们定义:

当我们用DOG算子代替LOG算子与图像卷积的时候:

近似的LOG算子值的选取:

当使用这个值时,可以保证LoG和DoG的过零点相同,只是幅度大小不同。

这样,我们只要对图像进行两次高斯平滑再将结果相减就可以近似得到LOG作用于图像的效果了!

1.2.1差分金字塔的建立

差分金字塔的是在高斯金字塔的基础上操作的,其建立过程是:在高斯金子塔中的每组中相邻两层相减(下一层减上一层)就生成高斯差分金字塔.

高斯差分金字塔其操作如下图:

1.2.2差分金字塔源码分析

2.空间极值点(即关键点)的检测

关键点是由DOG空间的局部极值点组成的,关键点的初步探查是通过同一组内各DoG相邻两层图像之间比较完成的。为了寻找DoG函数的极值点,每一个像素点要和它所有的相邻点比较,看其是否比它的图像域和尺度域的相邻点大或者小。如图下图所示,中间的检测点和它同尺度的8个相邻点和上下相邻尺度对应的9×2个点共26个点比较,以确保在尺度空间和二维图像空间都检测到极值点。

2.1极值点的检测过程

2.1.1极值点检测示意

2.1.2极值点检测源码分析

2.2关键点定位

以上方法检测到的极值点是离散空间的极值点,以下通过拟合三维二次函数来精确确定关键点的位置和尺度,同时去除低对比度的关键点和不稳定的边缘响应点(因为DoG算子会产生较强的边缘响应),以增强匹配稳定性、提高抗噪声能力。

2.2.1关键点精确定位

离散空间的极值点并不是真正的极值点,下图显示了二维函数离散空间得到的极值点与连续空间极值点的差别。利用已知的离散空间点插值得到的连续空间极值点的方法叫做子像素插值。

为了提高关键点的稳定性,需要对尺度空间DoG函数进行曲线插值。利用DoG函数在尺度空间的Taylor展开式(插值函数)为:

上面算式的矩阵表示如下:

 注意:此处D就是f,D(X)就是f(X)

其中,X求导并让方程等于零,可以得到极值点的偏移量为:

对应极值点,方程的值为:

其中, X^代表相对插值中心的偏移量,当它在任一维度上的偏移量大于0.5时(即x或y或 σ),意味着插值中心已经偏移到它的邻近点上,所以必须改变当前关键点的位置。同时在新的位置上反复插值直到收敛;也有可能超出所设定的迭代次数或者超出图像边界的范围,此时这样的点应该删除,在Lowe中进行了5次迭代。另外,过小的点易受噪声的干扰而变得不稳定,所以将 小于某个经验值(Lowe论文中使用0.03,Rob Hess等人实现时使用0.04/S)的极值点删除。同时,在此过程中获取特征点的精确位置(原位置加上拟合的偏移量)以及尺度(σ)。

 找极值点的证明:

注意:

关于向量求导,要看分母布局还是分子布局,第一项此处是分母布局(分子为行向量或者分母为列向量),所以求导后为(n*1)维的,此处应该没有转置符号

2.2.2消除边缘响应

一个定义不好的高斯差分算子的极值在横跨边缘的地方有较大的主曲率,而在垂直边缘的方向有较小的主曲率。DOG算子会产生较强的边缘响应,需要剔除不稳定的边缘响应点。获取特征点处的Hessian矩阵,主曲率通过一个2x2 的Hessian矩阵H求出(D的主曲率和H的特征值成正比):

假设H的特征值为α和β(α、β代表x和y方向的梯度)且α>β。令α=rβ则有:

其中Tr(H)求取H的对角元素和;Det(H)为求H的行列式值。

则公式(r+1)^2/r的值在两个特征值相等时最小,随着的增大而增大。值越大,说明两个特征值的比值越大,即在某一个方向的梯度值越大,而在另一个方向的梯度值越小,而边缘恰恰就是这种情况。所以为了剔除边缘响应点,需要让该比值小于一定的阈值,因此,为了检测主曲率是否在某域值r下,只需检测:

论文建议r=10,OpenCv也采用r=10

2.2.3精确定位中的泰勒插值源码分析

3.关键点方向分配

为了使描述符具有旋转不变性,需要利用图像的局部特征为给每一个关键点分配一个基准方向。使用图像梯度的方法求取局部结构的稳定方向。

3.1特征点的梯度

3.1.1梯度的计算

对于在DOG金字塔中检测出的关键点点,采集其所在高斯金字塔图像3σ领域窗口内像素的梯度和方向分布特征。梯度的模值和方向如下:

L为关键点所在的尺度空间值,按Lowe的建议,梯度的模值m(x,y)按 σ=1.5σ_oct 的高斯分布加成,按尺度采样的3σ原则,领域窗口半径为 3x1.5σ_oct。

说明:看下边链接,解释了为什么使用用x+1和x-1及y+1和y-1(模板用的[-1,0,1])

图像的梯度问题:

https://wenku.baidu.com/view/958ab556f02d2af90242a8956bec0975f465a49c.html

https://blog.csdn.net/image_seg/article/details/78790968

常见的图像梯度计算公式:

https://wenku.baidu.com/view/86d5e4a2ce2f0066f4332257.html

3.1.2梯度直方图

在完成关键点的梯度计算后,使用直方图统计领域内像素的梯度和方向。梯度直方图将0~360度的方向范围分为36个柱(bins),其中每柱10度。如图5.1所示,直方图的峰值方向代表了关键点的主方向,(为简化,图中只画了八个方向的直方图)。

3.2特征点主方向的确定

方向直方图的峰值则代表了该特征点处邻域梯度的方向,以直方图中最大值作为该关键点的主方向。为了增强匹配的鲁棒性,只保留峰值大于主方向峰值80%的方向作为该关键点的辅方向。因此,对于同一梯度值的多个峰值的关键点位置,在相同位置和尺度将会有多个关键点被创建但方向不同。仅有15%的关键点被赋予多个方向,但可以明显的提高关键点匹配的稳定性。实际编程实现中,就是把该关键点复制成多份关键点,并将方向值分别赋给这些复制后的关键点,并且,离散的梯度方向直方图要进行插值拟合处理,来求得更精确的方向角度值。

3.2.1梯度图像的平滑处理

为了防止某个梯度方向角度因受到噪声的干扰而突变,我们还需要对梯度方向直方图进行平滑处理。Opencv  所使用的平滑公式为:

之间的值,如h(-1) = h(35)。

3.2.2梯度直方图的抛物线插值

 

假设我们在第i个小柱子要找一个精确的方向,那么由上面分析知道:

设插值抛物线方程为h(t)=at2+bt+c,其中a、b、c为抛物线的系数,t为自变量,t∈[-1,1],此抛物线求导并令它等于0。

h(t)´=0 tmax=-b/(2a)

现在把这三个插值点带入方程可得:

3.2.3抛物线插值源码分析

至此,图像的关键点已检测完毕,每个关键点有三个信息:位置、所处尺度、方向。由此可以确定一个SIFT特征区域。

4.特征点描述符

通过以上步骤,对于每一个关键点,拥有三个信息:位置、尺度以及方向。接下来就是为每个关键点建立一个描述符,使其不随各种变化而改变,比如光照变化、视角变化等等。并且描述符应该有较高的独特性,以便于提高特征点正确匹配的概率。

4.1特征的生成过程

4.1.1确定计算描述子所需的区域

将关键点附近的区域划分为d*d(Lowe建议d=4)个子区域,每个子区域作为一个种子点,每个种子点有8个方向。考虑到实际计算时,需要采用三线性插值,所需图像窗口边长为3x3xσ_oct x(d+1)  。在考虑到旋转因素(方便下一步将坐标轴旋转到关键点的方向),如下图6.1所示,实际计算所需的图像区域半径为:



4.1.2坐标轴旋转至主方向

将坐标轴旋转为关键点的方向,以确保旋转不变性。

备注:关于Laplace拉普拉斯算子具有旋转不变性的数学公式证明和图像证明见我另一篇博客:为什么拉普拉斯算子具有旋转不变性

4.1.3梯度直方图的生成

将邻域内的采样点分配到对应的子区域内,将子区域内的梯度值分配到8个方向上,计算其权值。

旋转后的采样点 落在子区域的下标为

4.1.4三线性插值

采样点在子区域中的下标(x'',y'')                              (图中蓝色窗口内红色点)线性插值,计算其对每个种子点的贡献。如图中的红色点,落在第0行和第1行之间,对这两行都有贡献。对第0行第3列种子点的贡献因子为dr,对第1行第3列的贡献因子为1-dr,同理,对邻近两列的贡献因子为dc和1-dc,对邻近两个方向的贡献因子为do和1-do。则最终累加在每个方向上的梯度大小为:

其中k,m,n为0(像素点超出了对要插值区间的四个邻近子区间所在范围)或为1(像素点处在对要插值区间的四个邻近子区间之一所在范围)。

4.1.5特征描述子

如上统计的4*4*8=128个梯度信息即为该关键点的特征向量。
      特征向量形成后,为了去除光照变化的影响,需要对它们进行归一化处理,对于图像灰度值整体漂移,图像各点的梯度是邻域像素相减得到,所以也能去除。得到的描述子向量为H=(h1,h2,.......,h128),归一化后的特征向量为L=(L1,L2,......,L128),则

4.1.6描述子的门限化

非线性光照,相机饱和度变化对造成某些方向的梯度值过大,而对方向的影响微弱。因此设置门限值(向量归一化后,一般取0.2)截断较大的梯度值(大于0.2的则就令它等于0.2,小于0.2的则保持不变)。然后再进行一次归一化处理,提高特征的鉴别性。

4.2描述子相关分析

用一组图来概括描述子的生成过程

4.2.1描述子生成总括

 4.2.3描述子三线性插值源码分析

参考文献
1、sift算法详解及应用(课件)。(本文档简明扼要的简述了SIFT算法和图像匹配以及匹配修正。图文并茂,一览全貌)
  http://wenku.baidu.com/view/87270d2c2af90242a895e52e.html?re=view
2、SIFT算法详解(sift操作过程理论通俗,尤其是高阶泰勒展开式及高阶导数分析的很好,对理解亚像素定位拟合中的图像具体编程操作很有用)
  http://blog.csdn.net/zddblog/article/details/7521424
3、SIFT特征分析与源码解读(1模拟金字塔的过程解释的很详细,带有动画模拟;2 在寻找特征点进行亚像素定位拟合中的图像很形象)
  http://blog.csdn.net/xw20084898/article/details/16832755
4、【OpenCV】SIFT原理与源码分析:关键点描述(对关键点描述子区域的取舍讲解的很详细)
  http://blog.csdn.net/xiaowei_cqu/article/details/8113565
5、【OpenCV】SIFT原理与源码分析(对sift 算法采用分部分叙述且带有源码分析说明)
  http://blog.csdn.net/xiaowei_cqu/article/details/8069548
6、opencv2.4.9sift源码分析(1赵春江的这篇文章是我目前看到分析sift算法比较全面的;2尤其给出了使用三维直方图来分析三线性插值,对理解描述子的生成作用很大;3 给出了源码分析和演示结果)
  http://wenku.baidu.com/view/d7edd2464b73f242336c5ffa.html
  http://download.csdn.net/detail/zhaocj/8294793
7、九之再续:教你一步一步用c语言实现sift算法、下
(1算法中寻找主方向使用的抛物线插值拟合方法;2 描述子三次插值)
  http://blog.csdn.net/v_JULY_v/article/details/6246213
8、RobHess的SIFT源码分析:综述(各个子程序详解及分析很细致,一概全貌)
  http://blog.csdn.net/masibuaa/article/details/9191309
9、特征点检测学习_1(sift算法)(1这篇文章没有太多理论分析,但结合QT和OpenCV做出了生动的sift算法匹配演示,有图很直观生动呀,用程序配图一目了然;2 简述对robhess 的c版本sift代码在c++中的使用注意问题 )
  http://www.cnblogs.com/tornadomeet/archive/2012/08/16/2643168.html
10、OpenCV 中c版本sift源代码网址
  http://blogs.oregonstate.edu/hess/code/sift/
11、【特征匹配】SIFT原理与C源码剖析(这个也不错,图文并茂,还带有  源码分析,总体来说是以程序带动问题分析)
  http://blog.csdn.net/luoshixian099/article/details/47377611
12、插值与拟合(对多项式及其插值讲解还不错)
  http://wenku.baidu.com/link?url=wWcqLrpokQrjZZKzFbuJ4QDbZXZkMByCu-KaVKrSyGD6fh9Bpk1kZOPitpkFpNBw_no8UoyWY2DGQg9I7aL_tO3oi7z5mUK7cN8Sca6dX-O
13、线性插值与抛物线插值(对这两种插值讲解的很详细,是目前发现最 好的一版
       http://www.docin.com/p-711275966.html
14、奇异值分解(对奇异值怎么来的讲解比较细致)
       http://blog.sina.com.cn/s/blog_53eb0fdf0101sfu1.html

SIFT算法的更多相关文章

  1. SIFT算法详解(转)

    http://blog.csdn.net/zddblog/article/details/7521424 目录(?)[-] 尺度不变特征变换匹配算法详解 Scale Invariant Feature ...

  2. 【转】 SIFT算法详解

    尺度不变特征变换匹配算法详解Scale Invariant Feature Transform(SIFT)Just For Fun zdd  zddmail@gmail.com 对于初学者,从Davi ...

  3. SIFT算法的应用--目标识别之Bag-of-words模型

    原文:http://blog.csdn.net/v_JULY_v/article/details/6555899 SIFT算法的应用 -目标识别之用Bag-of-words模型表示一幅图像 作者:wa ...

  4. 《sift算法详解》阅读笔记

    原博客来自:http://blog.csdn.net/zddblog/article/details/7521424 定义: 尺度不变特征转化是一种计算机视觉算法,用于侦测和描述物体的局部性特征,在空 ...

  5. SIFT算法:特征描述子

    SIFT算法:DoG尺度空间生产  SIFT算法:KeyPoint找寻.定位与优化 SIFT算法:确定特征点方向  SIFT算法:特征描述子 目录: 1.确定描述子采样区域 2.生成描述子 2.1 旋 ...

  6. SIFT算法:确定特征点方向

    SIFT算法:DoG尺度空间生产  SIFT算法:KeyPoint找寻.定位与优化 SIFT算法:确定特征点方向  SIFT算法:特征描述子 目录: 1.计算邻域梯度方向和幅值 2.计算梯度方向直方图 ...

  7. SIFT算法:KeyPoint找寻、定位与优化

    SIFT算法:DoG尺度空间生产  SIFT算法:KeyPoint找寻.定位与优化 SIFT算法:确定特征点方向  SIFT算法:特征描述子 目录: 1.找寻 2.定位 3.优化 1 KeyPoint ...

  8. SIFT算法:DoG尺度空间生产

    SIFT算法:DoG尺度空间生产  SIFT算法:KeyPoint找寻.定位与优化 SIFT算法:确定特征点方向  SIFT算法:特征描述子 目录: 1.高斯尺度空间(GSS - Gauss Scal ...

  9. sift算法c语言实现

    前段时间在做三维測量方面的研究.须要得到物体表面三维数据.sift算法是立体匹配中的经典算法.以下是对RobHess的SIFT源码的凝视.部分内容參考网上,在这里向各位大神表示感谢. http://b ...

  10. SIFT算法大综合

     SIFT算法原理+参看资料+问题issue 参考书籍——<图像局部不变性特征与描述>王永明.王贵锦著 SIFT特征点提取——详见博客:https://blog.csdn.net/ling ...

随机推荐

  1. Docker基本命令与使用 —— Docker容器的网络连接(四)

    一.Docker容器的网络基础 通过ifconfig查看docker0的网络设备,docker守护进程就是通过docker0为docker的容器提供网络连接的各种服务. docker0是Linux虚拟 ...

  2. Windows和Linux查看端口占用

    Windows方法 TCP netstat -aon|findstr "TCP"|findstr "LISTENING"|findstr ":135[ ...

  3. [sharepoint]Rest api相关知识(转)

    写在前面 最近又开始弄rest api了,通过sharepoint rest api获取站点信息,Items,fields非常方便,再结合OData查询,更是得心应手.这里记录学习的时候用到的知识点, ...

  4. django之用户表的继承

    有这样一个场景,之前已经设计好了用户的信息表,但是再设计另外一个业务表的时候,信息有点重复,如何重新设计呢? 可以采用表的继承,让一个表作为基类,业务表就可以继承它 要注意以下几点 1 作为基类的表使 ...

  5. 浏览器局部打印实现,iframe打印

    const handleOk = () =>{ let ele = document.getElementById('printInfor'); let iframe=window.frames ...

  6. react portals

    来源:https://segmentfault.com/a/1190000011668286 Portals是react 16.3 提供的官方解决方案,使得组件可以脱离父组件层级挂载在DOM树的任何位 ...

  7. python_06 函数、全局变量与局部变量、函数递归

    函数 1.函数的定义: def 函数名(参数): #解释函数的功能 代码块 返回值 函数的定义主要有如下要点: def:表示函数的关键字 函数名:函数的名称,日后根据函数名调用函数 函数体:函数中进行 ...

  8. idea导入项目

    1. 2.导入项目 3.右键项目选择web 4.编辑添加tomcat 5.添加jar.包 6. 7.右键put into 8.安装tomcat 9.引入tomcat 10.把项目布署到tomcat

  9. BASIC GIT WORKFLOW

    BASIC GIT WORKFLOW Generalizations You have now been introduced to the fundamental Git workflow. You ...

  10. Centos安装ffmpeg

    yum install -y ffmpeg 使用上面的命令安装却出现以下问题: Google后发现缺少一些扩展: wget https://download1.rpmfusion.org/free/e ...