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

opencv计算机视觉--Harris角点检测SIFT特征提取图片抠图完整教程:从入门到实战部署

上周在生产环境遇到了这个问题,排查了2天才定位到原因。今天分享一下完整的解决方案,希望帮大家避坑。

一、Harris角点检测

1. 核心概念

  • 角点定义:图像中在两个垂直方向都有明显变化的像素点

  • 基本思想:通过分析图像局部窗口在各个方向移动时的灰度变化来判断是否为角点

  • 响应值:每个像素点计算出一个角点响应值,值越大表示越可能是角点

2. dst数组详解

dst = cv2.cornerHarris(gray, blockSize, ksize, k)
  • dst形状:与输入图像相同大小(height × width)

  • dst数据类型:float32

  • dst值含义:每个位置的值表示该像素点是角点的"可能性"或"响应强度"

    • 正值:可能是角点(值越大可能性越高)

    • 负值:平坦区域或边缘

    • 接近0:平坦区域

3. 关键函数

# 核心函数
cv2.cornerHarris(src, blockSize, ksize, k)

参数含义

  • src:输入灰度图像

  • blockSize:邻域大小(考虑像素点的窗口大小)

  • ksize:Sobel算子的孔径大小(用于计算梯度)

  • k:Harris检测器的经验参数(通常0.04-0.06)

4. 阈值处理原理

# 标记角点的标准方法
img[dst > 0.01 * dst.max()] = [0, 0, 255]
  • dst.max():获取整个响应图中的最大值

  • 0.01 * dst.max():设定阈值(最大值的1%)

  • 逻辑:只保留响应值大于阈值的像素点作为角点

二、SIFT特征提取

1. SIFT算法四个步骤

  1. 尺度空间极值检测:在不同尺度空间寻找稳定特征点

  2. 关键点精确定位:去除低对比度和边缘响应点

  3. 方向分配:为每个关键点分配主方向

  4. 描述符生成:生成128维特征向量

2. SIFT关键函数说明

创建SIFT对象
sift = cv2.SIFT_create()

创建SIFT检测器实例,可以设置参数控制特征点数量、对比度阈值等。

detect()函数
kp = sift.detect(image, mask=None)
  • 功能:只检测关键点的位置信息

  • 返回值:关键点列表(每个关键点包含位置、尺度、方向等信息)

  • kp属性

    • pt:坐标位置 (x, y)

    • size:关键点直径

    • angle:方向(角度)

    • response:响应强度

    • octave:金字塔层数

compute()函数
kp, des = sift.compute(image, kp)
  • 功能:为已检测的关键点计算描述符

  • 输入:图像 + 已检测的关键点

  • 输出

    优化建议:

    如果你的项目访问量较大,建议增加缓存机制。我们团队在优化后,接口响应时间从800ms降到了50ms, 效果非常明显。具体的缓存策略可以根据业务场景调整。

    • kp:更新后的关键点(添加了方向信息)

    • des:描述符数组(n×128)

detectAndCompute()函数
kp, des = sift.detectAndCompute(image, mask=None)
  • 功能:一步完成检测和计算(更高效)

  • 返回值:关键点列表 + 描述符数组

3. 描述符(des)详解

# des的结构
print(des.shape)  # 输出:(n, 128)
  • n:关键点数量

  • 128:每个关键点的特征向量维度

  • 数据特性

    • 对尺度、旋转、光照变化具有不变性

    • 对视角变化、仿射变换具有一定鲁棒性

4. 关键点(kp)与描述符(des)的关系

组件内容用途
关键点(kp)位置、尺度、方向、响应值定位特征位置
描述符(des)128维特征向量描述特征内容

类比理解

  • 关键点 ≈ 指纹的纹线交叉点(位置信息)

  • 描述符 ≈ 指纹的细节特征(内容信息)

  • 匹配:比较两张图片的描述符,找到相似的特征对

5.角点检测和特征提取对比

Harris角点检测流程
输入图像 → 灰度化 → Harris检测 → 响应图 → 阈值处理 → 标记角点
SIFT特征提取流程
输入图像 → 灰度化 → SIFT检测 → 关键点位置 → 计算描述符 → 特征向量(detect())         (compute())

6. 应用场景差异

Harris角点适合
  • 简单的角点检测需求

  • 实时性要求高的应用

  • 只需要位置信息,不需要特征描述

SIFT适合
  • 图像匹配和识别

  • 需要特征描述的应用

  • 对尺度、旋转变化有要求的场景

7. 核心区别总结

方面HarrisSIFT
输出角点响应值(单值)关键点+128维描述符
不变性旋转、光照尺度、旋转、光照
信息量位置信息位置+特征描述
复杂度简单快速复杂但功能强大

关键记住

  • Harris给出的是"每个像素可能是角点的概率"

  • SIFT给出的是"特征点的精确位置和详细描述"

  • 选择哪种方法取决于你的具体需求:

    • 只需要找到角点 → Harris

    • 需要匹配和识别 → SIFT

8.实际运用

Harris角点检测
import cv2
import numpy as np
# 角点检测部分
img = cv2.imread('005.jpg')
img=cv2.resize(img,dsize=None,fx=0.5,fy=0.5)
cv2.imshow('005',img)
cv2.waitKey(0)
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
dst = cv2.cornerHarris(gray, 4, 3, 0.04)
# 标记检测到的角点
img[dst > 0.01 * dst.max()] = [0, 0 , 255]
# 这里通过对角点响应进行阈值处理,标记出检测到的角点。
# 0.05 * dst.max() 是一个阈值,大于这个值的像素点会被标记为红色。
cv2.imshow('img', img)
cv2.waitKey(0)
cv2.destroyAllWindows()

SIFT特征提取
import cv2
import numpy as np
people = cv2.imread('peopleone.jpg')
people=cv2.resize(people,dsize=None,fx=0.5,fy=0.5)
cv2.imshow('people',people)
cv2.waitKey(0)
people_gray = cv2.cvtColor(people, cv2.COLOR_BGR2GRAY)
sift = cv2.SIFT_create()  # sift对象
kp = sift.detect(people)
# 查找关键点
people_sift = cv2.drawKeypoints(people, kp, None, flags=cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS)
cv2.imshow('people_sift', people_sift)
cv2.waitKey(0)
# 使用sift.compute()计算关键点描述符,方便后期的特征匹配
kp, des = sift.compute(people, kp)
print(np.array(kp).shape, des.shape)
cv2.destroyAllWindows()

三、图片抠图小案例

任务:

按照要求利用轮廓检测和按位与操作实现抠图功能。
有一张名为fan.jpg的图片,现要求使用 Python 结合 OpenCV 库编写代码实现以下功能:
(1)读取名为fan.jpg的图片,将尺寸设置为宽640,高480,然后逆时针旋转90度;
(2)使用Canny边缘检测提取(1)处理后的边缘;
(3)在提取边缘的基础上,查找轮廓并选取扇子的外轮廓,生成相应的掩模;
(4)通过掩模与原图进行按位与操作将对应部分提取出来,并保存为“shanzi.png”文件。

代码
import cv2
import numpy as np
def cv_show(name,img):cv2.imshow(name,img)cv2.waitKey(0)
image=cv2.imread('fan.jpg')
image=cv2.resize(image,(640,480))
cv_show('yuan',image)
rotated_image = np.rot90(image, k=1)
rotated_gray=cv2.cvtColor(rotated_image,cv2.COLOR_BGR2GRAY)
cv_show('rotated',rotated_image)
canny=cv2.Canny(rotated_gray,15,45)
cv_show('canny',canny)
cnts=cv2.findContours(canny,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)[-2]
cnts=sorted(cnts,key=cv2.contourArea,reverse=True)[:3]
if len(cnts) > 0:# 选取最大的轮廓(扇子通常是面积最大的)largest_contour = cnts[0]area = cv2.contourArea(largest_contour)print(f"最大轮廓面积: {area}")# 创建掩膜mask = np.zeros(rotated_gray.shape, dtype="uint8")cv2.drawContours(mask, [largest_contour], -1, 255, -1)  # -1表示填充cv_show('mask', mask)# 应用掩膜masked_image = cv2.bitwise_and(rotated_image, rotated_image, mask=mask)cv_show('masked_image', masked_image)cv2.imwrite('shanzi.png',masked_image)
cv2.destroyAllWindows()
运行结果

http://www.jsqmd.com/news/394715/

相关文章:

  • 北京办公隔断选哪家?2025年口碑厂家榜单揭晓,电动门/玻璃隔断/酒店隔断/感应门/办公室隔断,办公隔断设计推荐 - 品牌推荐师
  • 题解:洛谷 B2009 计算 (a+b)/c 的值
  • 题解:洛谷 B2007 A + B 问题
  • POST 方法是否能提交 @RequestParam的使用
  • 单北斗GNSS在变形监测系统中的应用与优势分析
  • 导师严选! 降AIGC工具 千笔 VS 云笔AI,研究生专属更高效!
  • 【雷达原理 学习笔记】至P69
  • 超越IDE:为什么AI正在将你的终端变成最智能的编程界面 - 详解
  • 【雷达原理学习笔记】64.P64目标距离测量(三)时间鉴别器的工作原理与数学模型 65.P65目标距离测量(四)
  • 如何在vs中使用Qt
  • 林区防火巡逻小车,识别烟雾明火巡山,输出火警预警。
  • 直接上结论:10个AI论文工具测评!继续教育毕业论文写作必备指南
  • 题解:洛谷 B2006 地球人口承载力估计
  • 直接上结论:9个AI论文网站测评!专科生毕业论文写作必备工具推荐
  • 一遍搞定全流程!当红之选的AI论文写作软件 —— 千笔·专业论文写作工具
  • 拖延症福音!降AIGC网站 千笔·专业降AIGC智能体 VS 灵感ai 专科生专属
  • FastAPI实战:WebSocket长连接保持与心跳机制,从入门到填坑
  • 题解:洛谷 B2004 对齐输出
  • 哪些柠檬酸酒精好氧菌种厂家值得关注?最新观察,市面上做得好的柠檬酸酒精好氧菌种公司口碑排行技术实力与市场口碑领航者 - 品牌推荐师
  • 《国产体系运维笔记》第2期:在 openEuler 24.03 LTS 上在线部署 Tomcat 9 全记录
  • Matlab图像去噪处理:还图像一片清晰天地
  • 题解:洛谷 B2003 输出第二个整数
  • 2026最新 APP隐私政策合规指南:全流程开发+检测+长效建设,规避监管风险、筑牢数据安全防线
  • YOLO26涨点改进 | 独家首发、注意力改进篇 | Arxiv 2025 | YOLO26引入PGSSA引导光谱自注意力,结合全局和局部光谱自注意力机制,提升局部细节识别,有效涨点起飞
  • 深入理解x86内存寻址:从8086实模式到IA-32段页式映射Linux内核实现
  • 高危预警|CVE-2025-4318 深度剖析:AWS Amplify Studio 远程代码执行漏洞(含完整复现+攻防对抗思路)
  • Content-Type 是 HTTP 请求 / 响应头中核心的字段
  • 一字致命:单字符误写(代|)引爆Firefox 0Day RCE漏洞,内核安全再敲警钟
  • Agent驱动·自主运维:Swimlane AI安全运营中心,重构网络安全防御新范式
  • Java 接口测试框架 Restassured