目前做网站,婚纱网站建设步骤和方法,装一个erp系统多少钱,重庆在建工程信息查询特征点检测与匹配是计算机视觉中的基础任务之一#xff0c;广泛应用于图像配准、物体识别、运动估计、三维重建等领域。下面是一些关键的知识点#xff1a;
1. 特征点检测
特征点检测的目的是从图像中找到独特的、稳定的点#xff0c;这些点在图像变化#xff08;如旋转、…特征点检测与匹配是计算机视觉中的基础任务之一广泛应用于图像配准、物体识别、运动估计、三维重建等领域。下面是一些关键的知识点
1. 特征点检测
特征点检测的目的是从图像中找到独特的、稳定的点这些点在图像变化如旋转、缩放、光照变化等中具有较好的鲁棒性。常见的特征点检测算法包括
SIFT描述符具有旋转和尺度不变性。SURF描述符加速的SIFT计算速度更快。ORB描述符结合了旋转不变的BRIEF描述符速度快且具有较好的性能。
1.1 Harris 角点检测器 Harris 角点检测器是最早的一种特征点检测方法通过计算图像的梯度找到角点。
import cv2
import numpy as np# 读取图像并转换为灰度图
img cv2.imread(example.jpg)
gray cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)# Harris 角点检测
gray np.float32(gray)
dst cv2.cornerHarris(gray, 2, 3, 0.04)# 结果通过膨胀标记角点
dst cv2.dilate(dst, None)# 设置阈值
img[dst 0.01 * dst.max()] [0, 0, 255]# 显示结果
cv2.imshow(Harris Corners, img)
cv2.waitKey(0)
cv2.destroyAllWindows()1.2 SIFT (Scale-Invariant Feature Transform) SIFT 是一种尺度不变特征变换算法能够检测并描述图像中的局部特征点。
import cv2# 读取图像并转换为灰度图
img cv2.imread(example.jpg)
gray cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)# 创建SIFT对象
sift cv2.SIFT_create()# 检测关键点和计算描述符
keypoints, descriptors sift.detectAndCompute(gray, None)# 在图像上绘制关键点
img_with_keypoints cv2.drawKeypoints(img, keypoints, None, flagscv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS)# 显示结果
cv2.imshow(SIFT Keypoints, img_with_keypoints)
cv2.waitKey(0)
cv2.destroyAllWindows()
1.3 ORB (Oriented FAST and Rotated BRIEF) ORB 是一种快速且高效的特征点检测与描述算法结合了FAST关键点检测器和BRIEF描述符。
import cv2# 读取图像并转换为灰度图
img cv2.imread(example.jpg, cv2.IMREAD_GRAYSCALE)# 创建ORB对象
orb cv2.ORB_create()# 检测关键点和计算描述符
keypoints, descriptors orb.detectAndCompute(img, None)# 在图像上绘制关键点
img_with_keypoints cv2.drawKeypoints(img, keypoints, None, color(0, 255, 0))# 显示结果
cv2.imshow(ORB
2. 特征点匹配
特征点匹配是将一幅图像中的特征点与另一幅图像中的特征点进行匹配以找到它们之间的对应关系。 2.1 Brute-Force匹配 Brute-Force匹配器逐一比较描述符并找到最相似的描述符对。
import cv2# 读取图像并转换为灰度图
img1 cv2.imread(image1.jpg, cv2.IMREAD_GRAYSCALE)
img2 cv2.imread(image2.jpg, cv2.IMREAD_GRAYSCALE)# 创建ORB对象
orb cv2.ORB_create()# 检测关键点和计算描述符
keypoints1, descriptors1 orb.detectAndCompute(img1, None)
keypoints2, descriptors2 orb.detectAndCompute(img2, None)# 创建Brute-Force匹配器
bf cv2.BFMatcher(cv2.NORM_HAMMING, crossCheckTrue)# 进行描述符匹配
matches bf.match(descriptors1, descriptors2)# 按距离排序
matches sorted(matches, keylambda x: x.distance)# 绘制匹配结果
img_matches cv2.drawMatches(img1, keypoints1, img2, keypoints2, matches[:10], None, flagscv2.DrawMatchesFlags_NOT_DRAW_SINGLE_POINTS)# 显示结果
cv2.imshow(ORB Matches, img_matches)
cv2.waitKey(0)
cv2.destroyAllWindows()
2.2 FLANN匹配 FLANN是快速最近邻搜索库适用于大数据集和高维特征的匹配。
import cv2
import numpy as np# 读取图像并转换为灰度图
img1 cv2.imread(image1.jpg, cv2.IMREAD_GRAYSCALE)
img2 cv2.imread(image2.jpg, cv2.IMREAD_GRAYSCALE)# 创建SIFT对象
sift cv2.SIFT_create()# 检测关键点和计算描述符
keypoints1, descriptors1 sift.detectAndCompute(img1, None)
keypoints2, descriptors2 sift.detectAndCompute(img2, None)# 设置FLANN匹配器参数
FLANN_INDEX_KDTREE 1
index_params dict(algorithmFLANN_INDEX_KDTREE, trees5)
search_params dict(checks50)# 创建FLANN匹配器
flann cv2.FlannBasedMatcher(index_params, search_params)# 进行描述符匹配
matches flann.knnMatch(descriptors1, descriptors2, k2)# 仅保留距离比率小于0.7的匹配
good_matches []
for m, n in matches:if m.distance 0.7 * n.distance:good_matches.append(m)# 绘制匹配结果
img_matches cv2.drawMatches(img1, keypoints1, img2, keypoints2, good_matches, None, flagscv2.DrawMatchesFlags_NOT_DRAW_SINGLE_POINTS)# 显示结果
cv2.imshow(SIFT FLANN Matches, img_matches)
cv2.waitKey(0)
cv2.destroyAllWindows()
3.单应性矩阵
单应性矩阵Homography Matrix是一种用于描述两个平面间映射关系的3x3矩阵常用于图像配准、图像拼接和透视变换等应用中。在计算机视觉中通过计算单应性矩阵可以将一个图像中的点映射到另一个图像中的对应点从而实现图像的对齐和变换。
计算单应性矩阵
为了计算单应性矩阵我们需要至少四对对应的点即源图像中的点和目标图像中的点。OpenCV提供了cv2.findHomography函数来计算单应性矩阵。
基本步骤
读取图像并检测特征点匹配特征点计算单应性矩阵应用单应性矩阵进行图像变换
下面是一个详细的示例代码
import cv2
import numpy as np# 读取源图像和目标图像
src_img cv2.imread(source.jpg)
dst_img cv2.imread(destination.jpg)# 转换为灰度图像
src_gray cv2.cvtColor(src_img, cv2.COLOR_BGR2GRAY)
dst_gray cv2.cvtColor(dst_img, cv2.COLOR_BGR2GRAY)# 使用ORB检测关键点和描述符
orb cv2.ORB_create()
src_keypoints, src_descriptors orb.detectAndCompute(src_gray, None)
dst_keypoints, dst_descriptors orb.detectAndCompute(dst_gray, None)# 使用Brute-Force匹配器进行特征点匹配
bf cv2.BFMatcher(cv2.NORM_HAMMING, crossCheckTrue)
matches bf.match(src_descriptors, dst_descriptors)# 按距离排序匹配结果
matches sorted(matches, keylambda x: x.distance)# 确保有足够的匹配点对
if len(matches) 4:# 提取匹配的点坐标src_pts np.float32([src_keypoints[m.queryIdx].pt for m in matches]).reshape(-1, 1, 2)dst_pts np.float32([dst_keypoints[m.trainIdx].pt for m in matches]).reshape(-1, 1, 2)# 计算单应性矩阵H, mask cv2.findHomography(src_pts, dst_pts, cv2.RANSAC, 5.0)# 使用单应性矩阵对源图像进行透视变换height, width, channels dst_img.shapewarped_img cv2.warpPerspective(src_img, H, (width, height))# 显示结果cv2.imshow(Warped Image, warped_img)cv2.waitKey(0)cv2.destroyAllWindows()
else:print(Not enough matches found - {}/{}.format(len(matches), 4))详细说明
ORB特征点检测和描述使用ORB算法检测关键点和描述符。特征点匹配使用Brute-Force匹配器对检测到的特征点进行匹配。检查匹配点对数量在计算单应性矩阵之前确保有足够的匹配点对至少4对。计算单应性矩阵和透视变换如果有足够的匹配点对计算单应性矩阵并进行透视变换否则输出提示信息。
4.项目
用于将两张图像拼接在一起生成一个全景图。以下是代码的主要步骤和功能
1.读取和预处理图像
代码首先读取了两张图片map1.png 和 map2.png。然后将两张图片调整到相同的尺寸640x480。 2.特征点检测和匹配使用SIFTScale-Invariant Feature Transform算法检测两张图像中的特征点并计算特征描述子。创建一个BFMatcherBrute-Force Matcher对象来进行特征匹配。使用knnMatch方法找到两张图像中的特征点匹配对并根据距离筛选有效的匹配点。
3.计算单应性矩阵
通过有效的特征匹配点计算单应性矩阵Homography Matrix这个矩阵用于将一张图像变换到另一张图像的坐标系中。 4.图像变换与拼接使用单应性矩阵将第一张图像进行透视变换。计算结果图像的尺寸并创建一个新的大图像将变换后的第一张图像和第二张图像拼接在一起。 5.显示结果最后将拼接后的结果图像显示出来。
具体代码解释如下
import cv2
import numpy as npdef stitch_image(img1, img2, H):# 获得原始图的高/宽h1, w1 img1.shape[:2]h2, w2 img2.shape[:2]# 获取图像的四个角点img1_dims np.float32([[0,0], [0, h1], [w1, h1], [w1, 0]]).reshape(-1, 1, 2)img2_dims np.float32([[0,0], [0, h2], [w2, h2], [w2, 0]]).reshape(-1, 1, 2)# 对第一张图像的角点进行透视变换img1_transform cv2.perspectiveTransform(img1_dims, H)# 计算结果图像的尺寸result_dims np.concatenate((img2_dims, img1_transform), axis0)[x_min, y_min] np.int32(result_dims.min(axis0).ravel() - 0.5)[x_max, y_max] np.int32(result_dims.max(axis0).ravel() 0.5)# 平移的距离transform_dist [-x_min, -y_min]# 平移矩阵transform_array np.array([[1, 0, transform_dist[0]],[0, 1, transform_dist[1]],[0, 0, 1]])# 对第一张图像进行透视变换和平移result_img cv2.warpPerspective(img1, transform_array.dot(H), (x_max-x_min, y_max-y_min))# 将第二张图像拼接到结果图像上result_img[transform_dist[1]:transform_dist[1]h2, transform_dist[0]:transform_dist[0]w2] img2return result_imgdef get_homo(img1, img2):# 创建SIFT特征检测对象sift cv2.xfeatures2d.SIFT_create()# 检测特征点和计算描述子k1, d1 sift.detectAndCompute(img1, None)k2, d2 sift.detectAndCompute(img2, None)# 创建特征匹配器bf cv2.BFMatcher()matches bf.knnMatch(d1, d2, k2)# 过滤特征匹配点verify_ratio 0.8verify_matches []for m1, m2 in matches:if m1.distance 0.8 * m2.distance:verify_matches.append(m1)min_matches 8if len(verify_matches) min_matches:img1_pts []img2_pts []for m in verify_matches:img1_pts.append(k1[m.queryIdx].pt)img2_pts.append(k2[m.trainIdx].pt)img1_pts np.float32(img1_pts).reshape(-1, 1, 2)img2_pts np.float32(img2_pts).reshape(-1, 1, 2)# 计算单应性矩阵H, mask cv2.findHomography(img1_pts, img2_pts, cv2.RANSAC, 5.0)return Helse:print(err: Not enough matches!)exit()# 读取两张图片
img1 cv2.imread(map1.png)
img2 cv2.imread(map2.png)# 将两张图片设置成同样大小
img1 cv2.resize(img1, (640, 480))
img2 cv2.resize(img2, (640, 480))inputs np.hstack((img1, img2))# 获得单应性矩阵
H get_homo(img1, img2)# 进行图像拼接
result_image stitch_image(img1, img2, H)cv2.imshow(input img, result_image)
cv2.waitKey()