当前位置: 首页 > news >正文

OpenCV ORB角点检测匹配和偏移计算

OpenCV ORB角点检测匹配和偏移计算

  • 1. 简介
  • 2. ORB角点检测匹配和偏移计算
    • 2.1. 创建平移图片
    • 2.2. ORB角点检测
    • 2.3. ORB角点匹配
    • 2.4. 计算变换矩阵


1. 简介

首先通过 cv2.ORB_create 创建ORB检测器 orb
然后通过 orb.detectAndCompute 检测两张图片获得ORB角点,
接着通过匹配器 cv2.BFMatcher 进行配对,
最后通过 cv2.findHomography 计算变换矩阵。


2. ORB角点检测匹配和偏移计算


2.1. 创建平移图片

首先我们先创建一个平移图片作为两个比较的图片

from cv2 import cv2
import numpy as np# 读取图片文件
demo_file_path = 'img1.png'
img = cv2.imdecode(np.fromfile(demo_file_path, dtype=np.uint8), cv2.IMREAD_UNCHANGED)
cv2.imshow('origin img', img)# 平移变量
T_x, T_y = 10, 20# 旋转变量 0°
angles = 0
sin_phi, cos_phi = np.sin(np.radians(angles)), np.cos(np.radians(angles))# 构造仿射变换矩阵H 2*3
H = np.float32([[cos_phi, -sin_phi, T_x],[sin_phi, cos_phi, T_y]])
np.set_printoptions(suppress=True)
print(H)# 仿射变换
new_img = cv2.warpAffine(img, H, (img.shape[1], img.shape[0]))# 保存图片
cv2.imencode('.png', new_img)[1].tofile('img2.png')
cv2.imshow('new img', new_img)
cv2.waitKey(0)

平移x轴10个像素点,y轴20个像素点,其他不变,如下图所示:

在这里插入图片描述
仿射变换矩阵 H H H,这里纯平移,所以也是就平移矩阵,如下:

[[ 1. -0. 10.][ 0.  1. 20.]]

关于透视变换参考:《OpenCV 透视变换》


2.2. ORB角点检测

import cv2
import numpy as np# 读取两个连续图像
img1 = cv2.imread('img1.png')
img2 = cv2.imread('img2.png')# 初始化ORB检测器
orb = cv2.ORB_create(nfeatures=500)# 检测关键点和描述符
kp1, des1 = orb.detectAndCompute(img1, None)
kp2, des2 = orb.detectAndCompute(img2, None)# 显示ORB角点
keypoints_img1 = cv2.drawKeypoints(img1, kp1, None, color=(0,255,0), flags=0)
keypoints_img2 = cv2.drawKeypoints(img2, kp2, None, color=(0,255,0), flags=0)
cv2.imshow('Keypoints Image1', keypoints_img1)
cv2.imshow('Keypoints Image2', keypoints_img2)

首先通过 cv2.ORB_create 创建ORB检测器 orb
然后通过 orb.detectAndCompute 检测两张图片获得ORB角点
然后通过 cv2.drawKeypoints 将角点可视化,如下图:

在这里插入图片描述


2.3. ORB角点匹配

# 创建匹配器
bf = cv2.BFMatcher(cv2.NORM_HAMMING, crossCheck=True)
matches = bf.match(des1, des2)# 根据匹配结果排序,取较优的50个
matches = sorted(matches, key = lambda x:x.distance)[:50]# 显示匹配关系
matches_img = cv2.drawMatches(img1, kp1, img2, kp2, matches, None, flags=2)
cv2.imshow('Matches Image', matches_img)

通过 cv2.BFMatcher 创建匹配器,其中有两个参数:

  1. normType:它指定要使用的距离量度。
    默认是 cv2.NORM_L2,对于SIFT,SURF 效果较佳
    对于二进制字符串的描述子,比如ORB,BRIEF,BRISK等,应该用cv2.NORM_HAMMING(汉明距离度量)
    使用,如果ORB检测器的 WTA_K 设置 3或者4,应该用cv2.NORM_HAMMING2

  2. crossCheck:匹配器为每个查询描述符找到 k 个距离最近的匹配描述符;
    默认为 False,为 True 时,只返回满足交叉验证条件的匹配结果。

在这里插入图片描述


2.4. 计算变换矩阵

# 提取匹配点
src_pts = np.float32([kp1[m.queryIdx].pt for m in matches]).reshape(-1,1,2)
dst_pts = np.float32([kp2[m.trainIdx].pt for m in matches]).reshape(-1,1,2)# 计算变换矩阵
H, mask = cv2.findHomography(src_pts, dst_pts, cv2.RANSAC, 5.0)
matchesMask = mask.ravel().tolist()  # 可用于cv2.drawMatches可视化匹配关系的掩模
np.set_printoptions(suppress=True)
print(H)# 可视化变换结果
offset_img = cv2.warpPerspective(img1, H, (img1.shape[1], img1.shape[0]))
cv2.imshow('Offset Image', offset_img)cv2.waitKey(0)
cv2.destroyAllWindows()

提取匹配点两个图片的src_ptsdst_pts,通过 cv2.findHomography 计算变换矩阵
可以看到计算出来的透视变换矩阵可以看到结果为x轴平移,与实际一致

[[ 1.  0. 10.][-0.  1. 20.][-0.  0.  1.]]

那么,显示变换结果也将一致,如下图:

在这里插入图片描述


谢谢

相关文章:

OpenCV ORB角点检测匹配和偏移计算

OpenCV ORB角点检测匹配和偏移计算 1. 简介2. ORB角点检测匹配和偏移计算2.1. 创建平移图片2.2. ORB角点检测2.3. ORB角点匹配2.4. 计算变换矩阵 1. 简介 首先通过 cv2.ORB_create 创建ORB检测器 orb, 然后通过 orb.detectAndCompute 检测两张图片获得ORB角点&…...

图文详解ChatGPT-o1完成论文写作的全流程

学境思源,一键生成论文初稿: AcademicIdeas - 学境思源AI论文写作 本月中旬OpenAI发布了OpenAI o1系列新的AI模型。 据OpenAI介绍,这些模型旨在花更多时间思考后再做出反应,就像人一样。通过训练,它们学会改进思维过…...

在线体验Sketch中文版,免费下载即刻上手!

Sketch是一款轻量而高效的矢量设计工具,助力全球设计师创造了诸多惊艳作品。安装Sketch的优势主要体现在其矢量编辑、控件和样式功能上。而下载安装“Sketch中文版”即时设计同样出色,它作为一站式设计平台,功能更全面。即时设计拥有纯中文的…...

Redis——缓存

目录 前言 一、缓存基本概念 1.概念 2.二八定律 二、使用 Redis 作为缓存 三、缓存的更新策略 1.定期生成 2.实时生成 四、Redis 内存淘汰机制 1.通用淘汰策略 (1)FIFO (2)LRU (3)LFU &#…...

RHCSA笔记三

第二章 linux中执行命令 命令格式 命令分为两类 内置命令:由 shell 程序自带的命令 外部命令:有独立的可执行程序文件,文件名即命令名 格式 主命令 参数 操作对象 # 注意: 下面是对于命令的语法的一些符号的说明&#xff1…...

【python】sorted() list.sort()

文章目录 sorted()和list.sort()sorted 函数sorted()根据键对字典排序根据字典的键排序根据字典的值排序将排序结果转换回字典 list.sort() 方法总结 keylambda student: student[age] sorted()和list.sort() 在Python中,sorted 函数和 list.sort() 方法都可以用来…...

训练集alpaca、sharegpt格式

LLaMA-Factory微调支持的格式 支持 alpaca 格式和 sharegpt 格式的数据集。 Alpaca格式 格式: [{"instruction": "人类指令(必填)","input": "人类输入(选填)","output": "模型回答(必填)","syst…...

Hive的数据存储格式

目录 一、前言 二、存储格式 2.1、文本格式(TextFile) 2.1.1、定义与特点 2.1.2、存储与压缩 2. 1.3、使用场景 2.2、行列式文件(ORCFile) 2.2.1、ORC的结构 2.2.2、ORC的数据类型 2.2.3、ORC的压缩格式 2.2.3、ORC存储…...

Linux Rsyslog 配置

1、Linux Rsyslog客户端配置 1)安装rsyslog yum install rsyslog 2)启用TCP或UDP传输 vim /etc/rsyslog.conf# Provides UDP syslog reception #若启用UDP进行传输,则取消下面两行的注释 #$ModLoad imudp #$UDPServerRun 514# Provide…...

python实现放烟花效果庆祝元旦

马上就要2025年元旦啦,提前祝大家新年快乐 完整代码下载地址:https://download.csdn.net/download/ture_mydream/89926458...

模型训练识别手写数字(二)

模型训练识别手写数字(一)使用手写数字图像进行模型测试 一、生成手写数字图像 1. 导入所需库 import cv2 import numpy as np import oscv2用于计算机视觉操作。 numpy用于处理数组和图像数据。 os用于文件和目录操作。 2. 初始化画布 canvas np.z…...

深入Vue2

frontend Vue2 学习内容参考 /在线运行 Element 学习内容参考 /视频教学 vue2 1. vue 实例 当一个 Vue 实例被创建时,它将 data 对象中的所有的 property 加入到 Vue 的响应式系统中 但是当使用Object.freeze(),会阻止修改现有的 property&#x…...

opencv-rust 系列3: Create_mask

前言: 这里只是opencv-rust自带示例的中文注解. 略微增加了一些代码也是我在调试时用到的. 调试方法可参见前文. 一. 这个程序还是有点难度的, 关键点在于: 创建了遮罩. 直接调用一个函数, 还是很简单的.窗口事件处理. 注册窗口回调函数, 用以处理鼠标事件进程同步和互斥锁. 为…...

Go语言初识

一、Go语言概述 Go语言是为了取代C和java的地位,既要保留C的简洁,也追求java的规模化开发 并行及分布式的支持,使得开发多核及多机器集群程序如同单机一样简单 Go语言从语言级别支持协程(goroutine, 轻量级线程),Go语言…...

Android Activity SingleTop启动模式使用场景

通知栏 当用户点击通知栏中的通知时,可以使用单顶启动模式来打开对应的活动,并确保只有一个实例存在。 简单集成极光推送 创建应用 获取appkey参数 切换到极光工作台 极光sdk集成 Project 根目录的主 gradle 配置 Module 的 gradle 配置 Jpush依赖配置 配置推送必须…...

PHP 代码执行相关函数

函数 说明 示例代码 ${} 用于复杂的变量解析,通常在字符串内用来解析变量或表达式。可以配合 eval 或其他动态执行代码的功能,用于间接执行代码。 eval(${flag}); eval() 用于执行一个字符串作为 PHP 代码。可以执行任何有效的 PHP 代码片段。没有…...

五周年,继续破浪前行

五周年,TapData 再一次带着自己的“乘风破浪”大队,在一个阳光明媚的日子里,把生日过在了海上。 头顶日升日落,这条属于全体 Tap-pers 的航船,再次校准航向,在船长的带领下,驶向下一个晴好的明…...

【操作系统】Linux之进程管理一

第1关:获取进程常见属性 ret.pidgetpid(); ret.ppidgetppid(); 第2关:进程创建操作-fork pid_t pid fork(); if(pid-1) printf("创建进程失败!"); else if(pid0) printf("Children"); else printf("Parent"); …...

C语言_数据在内存中的存储

1. 整数在内存中的存储 计算机中的整数有三种2进制表示方法 :原码、反码、补码。 三种表示方式均有符号位和数值位两个部分,最高一位的是符号位,剩下的都是数值位。符号位用“0”表示“正”,用“1”表示“负”。 正数的原、反、…...

华为原生鸿蒙操作系统:我国移动操作系统的新篇章

华为原生鸿蒙操作系统:我国移动操作系统的新篇章 引言 在移动操作系统领域,苹果iOS和安卓系统一直占据主导地位。然而,随着华为原生鸿蒙操作系统的正式发布,这一格局正在发生深刻变化。作为继苹果iOS和安卓系统后的全球第三大移动…...

在软件开发中正确使用MySQL日期时间类型的深度解析

在日常软件开发场景中,时间信息的存储是底层且核心的需求。从金融交易的精确记账时间、用户操作的行为日志,到供应链系统的物流节点时间戳,时间数据的准确性直接决定业务逻辑的可靠性。MySQL作为主流关系型数据库,其日期时间类型的…...

【Python】 -- 趣味代码 - 小恐龙游戏

文章目录 文章目录 00 小恐龙游戏程序设计框架代码结构和功能游戏流程总结01 小恐龙游戏程序设计02 百度网盘地址00 小恐龙游戏程序设计框架 这段代码是一个基于 Pygame 的简易跑酷游戏的完整实现,玩家控制一个角色(龙)躲避障碍物(仙人掌和乌鸦)。以下是代码的详细介绍:…...

多模态2025:技术路线“神仙打架”,视频生成冲上云霄

文|魏琳华 编|王一粟 一场大会,聚集了中国多模态大模型的“半壁江山”。 智源大会2025为期两天的论坛中,汇集了学界、创业公司和大厂等三方的热门选手,关于多模态的集中讨论达到了前所未有的热度。其中,…...

AtCoder 第409​场初级竞赛 A~E题解

A Conflict 【题目链接】 原题链接:A - Conflict 【考点】 枚举 【题目大意】 找到是否有两人都想要的物品。 【解析】 遍历两端字符串,只有在同时为 o 时输出 Yes 并结束程序,否则输出 No。 【难度】 GESP三级 【代码参考】 #i…...

什么是库存周转?如何用进销存系统提高库存周转率?

你可能听说过这样一句话: “利润不是赚出来的,是管出来的。” 尤其是在制造业、批发零售、电商这类“货堆成山”的行业,很多企业看着销售不错,账上却没钱、利润也不见了,一翻库存才发现: 一堆卖不动的旧货…...

零基础设计模式——行为型模式 - 责任链模式

第四部分:行为型模式 - 责任链模式 (Chain of Responsibility Pattern) 欢迎来到行为型模式的学习!行为型模式关注对象之间的职责分配、算法封装和对象间的交互。我们将学习的第一个行为型模式是责任链模式。 核心思想:使多个对象都有机会处…...

数据库分批入库

今天在工作中,遇到一个问题,就是分批查询的时候,由于批次过大导致出现了一些问题,一下是问题描述和解决方案: 示例: // 假设已有数据列表 dataList 和 PreparedStatement pstmt int batchSize 1000; // …...

Android15默认授权浮窗权限

我们经常有那种需求,客户需要定制的apk集成在ROM中,并且默认授予其【显示在其他应用的上层】权限,也就是我们常说的浮窗权限,那么我们就可以通过以下方法在wms、ams等系统服务的systemReady()方法中调用即可实现预置应用默认授权浮…...

3-11单元格区域边界定位(End属性)学习笔记

返回一个Range 对象,只读。该对象代表包含源区域的区域上端下端左端右端的最后一个单元格。等同于按键 End 向上键(End(xlUp))、End向下键(End(xlDown))、End向左键(End(xlToLeft)End向右键(End(xlToRight)) 注意:它移动的位置必须是相连的有内容的单元格…...

优选算法第十二讲:队列 + 宽搜 优先级队列

优选算法第十二讲:队列 宽搜 && 优先级队列 1.N叉树的层序遍历2.二叉树的锯齿型层序遍历3.二叉树最大宽度4.在每个树行中找最大值5.优先级队列 -- 最后一块石头的重量6.数据流中的第K大元素7.前K个高频单词8.数据流的中位数 1.N叉树的层序遍历 2.二叉树的锯…...