文章目录
- 一、Harris 角点检测
- 1.基本思想
- 2.检测步骤
- 3.OpenCV实现
- 二、SIFT特征检测
- 1. SIFT特征检测的基本原理
- 2. SIFT特征检测的特点
- 3. OpenCV 实现
一、Harris 角点检测
OpenCV中的Harris角点检测是一种基于图像灰度值变化的角点提取算法,它通过计算每个像素点的响应函数来确定是否为角点。Harris角点检测算法的基本思想和步骤如下:
1.基本思想
Harris角点检测算法基于图像中角点的局部特征,角点处图像灰度变化明显,且向任何方向移动变化都很大。通过计算每个像素点的响应函数,并设置阈值来确定角点。
2.检测步骤
-
灰度化:将彩色图像转换为灰度图像,以便进行后续处理。
-
计算图像梯度:使用Sobel等算子计算图像在x和y方向上的梯度。这些梯度反映了图像在水平和垂直方向上的亮度变化。
-
计算梯度积方向矩阵(自相关矩阵):对于每个像素点,根据其周围的梯度值计算自相关矩阵。这个矩阵包含了该点x方向梯度的平方和、y方向梯度的平方和以及x方向梯度与y方向梯度的乘积。
-
计算角点响应函数:根据自相关矩阵计算Harris响应函数,其定义为 R = det ( M ) − k ⋅ trace ( M ) 2 R = \text{det}(M) - k \cdot \text{trace}(M)^2 R=det(M)−k⋅trace(M)2,其中 M M M为自相关矩阵, det ( M ) \text{det}(M) det(M)为其行列式, trace ( M ) \text{trace}(M) trace(M)为其迹, k k k为一个经验参数,通常在0.04到0.06之间。
-
非极大值抑制:对于计算得到的响应函数图像,进行非极大值抑制,即保留局部最大值点,将其余点设为0,以消除重复检测的角点。
-
阈值化:根据设定的阈值,将响应函数图像中低于阈值的点排除,以得到最终的角点位置。
3.OpenCV实现
在OpenCV中,可以使用cv2.cornerHarris()
函数来实现Harris角点检测。该函数的基本语法如下:
dst = cv2.cornerHarris(src, blockSize, ksize, k[, dst[, borderType]])
-
src:输入图像,应为单通道灰度图像,数据类型为float32。
-
blockSize:角点检测中使用的邻域大小,一般为2、3、4等奇数。
-
ksize:Sobel算子的大小,用于计算x和y方向的梯度,一般为3。
-
k:Harris角点检测方程中的自由参数,一般取值为0.04到0.06。
-
dst:输出图像,与输入图像大小相同,数据类型为float32,其中每个像素点的值表示该点的Harris响应函数值。
-
borderType:像素的边界模式,默认值为
cv2.BORDER_DEFAULT
。 -
下图为示例图片
-
Harris角点检测代码实现
import cv2 # 读取图像并转换为灰度图像 image = cv2.imread('Ta.png') gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) # 计算Harris角点响应图像 dst = cv2.cornerHarris(gray, blockSize=4, ksize=3, k=0.04) # 标记检测到的角点 image[dst > 0.05 * dst.max()] = [0, 255, 0] # 这里通过对角点响应进行阈值处理,标记出检测到的角点 # 0.05 * dst.max()是一个值,大于这个值的像素点会被标记为绿色。 # 显示结果图像 cv2.imshow('Harris Corners', image) cv2.waitKey(0) cv2.destroyAllWindows()
-
结果如下:
二、SIFT特征检测
**SIFT(Scale-Invariant Feature Transform,尺度不变特征变换)**是一种在图像处理和计算机视觉领域广泛使用的特征检测算法。它主要用于检测图像中的局部特征点,并生成对应的描述符,这些特征点对图像的旋转、尺度缩放和亮度变化具有一定的不变性,同时对视角变化、仿射变换和噪声也保持一定程度的稳定性。以下是SIFT特征检测的详细介绍:
1. SIFT特征检测的基本原理
SIFT算法通过以下几个步骤来实现特征点的检测和描述:
-
尺度空间极值检测:
- 搜索所有尺度上的图像位置,通过高斯微分函数来识别潜在的对于尺度和旋转不变的兴趣点。
- 构建高斯金字塔和DoG(Difference of Gaussian)金字塔,通过比较相邻尺度图像的差分来检测极值点。
-
关键点定位:
- 在每个候选的位置上,通过拟合精细的模型(如泰勒展开)来确定关键点的精确位置和尺度。
- 关键点的选择依据于它们的稳定程度,通常选择局部极值点作为关键点。
-
方向确定:
- 基于图像局部的梯度方向,为每个关键点分配一个或多个主方向。
- 通过计算关键点周围区域的梯度幅值和方向来确定主方向,以实现旋转不变性。
-
关键点描述:
- 在每个关键点周围的邻域内,在选定的尺度上测量图像局部的梯度。
- 将这些梯度变换成一种表示,形成关键点的描述符。描述符由关键点周围的梯度方向直方图组成,通过拼接子区域的直方图来形成最终的描述符。
- 对描述符进行归一化处理,以增强其鲁棒性。
- 可结合以下图片理解
2. SIFT特征检测的特点
- 独特性:SIFT特征具有很好的独特性,即使在复杂的场景中也能有效地区分不同的特征点。
- 多量性:即使图像中只包含少数几个物体,也能产生大量的SIFT特征向量,为匹配提供更多的可能性。
- 高速性:经过优化的SIFT匹配算法可以达到实时的要求,适用于需要快速处理的应用场景。
- 可扩展性:SIFT特征可以很方便地与其他形式的特征向量进行联合,提高匹配的准确性和鲁棒性。
3. OpenCV 实现
- 步骤:
- 1.加载图像
- 2.创建SIFT对象
- 3.检测关键点和计算描述符
- 4.绘制关键点
- 5.显示图像
- 下图为特征检测的图片
- SIFT特征检测代码实现
import cv2 # 加载图像并转换为灰度图 image = cv2.imread('sea.jpg') image_gray = cv2.cvtColor(image, cv2.COLOR_BGR2RGB) # 在OpenCV中,使用cv2.SIFT_create()或cv2.xfeatures2d.SIFT_create()函数(取决于OpenCV的版本和配置)来创建一个SIFT对象。 # 这个对象将用于后续的关键点检测和描述符生成。 sift = cv2.SIFT_create() # 或者在某些OpenCV版本中可能需要 # sift = cv2.xfeatures2d.SIFT_create() # 使用SIFT对象的detectAndCompute()方法来检测图像中的关键点并计算它们的描述符 keypoints, descriptors = sift.detectAndCompute(image_gray, None) # 使用cv2.drawKeypoints()函数将检测到的关键点绘制到图像上 image_with_keypoints = cv2.drawKeypoints(image, keypoints, None, flags=cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS) # 显示图像 cv2.imshow('Image with Keypoints', image_with_keypoints) cv2.waitKey(0) # 等待任意键盘按键 cv2.destroyAllWindows() # 关闭所有OpenCV窗口
- 结果如下: