【opencv】图像处理(二)

前文指引

一、使用到的图片

一、梯度计算

原始图片

img = cv2.imread('circle.jpg')plt.imshow(img)
plt.show()

sobel算子

使用两个核 Gx = [[-1,0,1], [-2,0,2], [-1,0,1]] Gy = [[-1,-2,-1], [0,0,0], [1,2,1]]

dst = cv2.Sobel(src, ddepth, dx, dy, ksize)

  • ddepth 深度 -1
  • dx,dy 水平和竖直的方向
  • ksize 核大小

x方向上计算梯度

# CV_64F带负数
sobelx = cv2.Sobel(img, cv2.CV_64F,1,0,ksize = 3)
# 取绝对值,否则左边是白-黑大于0, 右边是黑-白小于0
sobelx = cv2.convertScaleAbs(sobelx)plt.imshow(sobelx)
plt.show()

opencv梯度计算x方向.png

y方向上计算梯度

sobely = cv2.Sobel(img, cv2.CV_64F,0,1,ksize = 3)
sobely = cv2.convertScaleAbs(sobely)plt.imshow(sobely)
plt.show()

opencv梯度计算y方向.png

猫图像计算梯度获得边缘

cat = cv2.imread('cat.jpg', cv2.IMREAD_GRAYSCALE)
sobelx = cv2.convertScaleAbs(cv2.Sobel(cat, cv2.CV_64F,1,0,ksize = 3))
sobely = cv2.convertScaleAbs(cv2.Sobel(cat, cv2.CV_64F,0, 1,ksize = 3))
sobelxy = cv2.addWeighted(sobelx,0.5,sobely,0.5, 0)plt.figure(figsize=(20,15))
plt.subplot(121)
plt.imshow(cat, cmap='gray')
plt.subplot(122)
plt.imshow(sobelxy, cmap='gray')
plt.show()

opencv梯度计算.png

二、边缘检测

Canny边缘检测

  1. 使用高斯滤波器,平滑图像,消除噪点
  2. 计算图像每个像素点的梯度强度和方向
  3. 应用非极大值抑制,消除边缘检测带来的杂散效应
  • 线性插值法,计算M(Q)点为w * M(g1) + (1 - w) * M(g2)
  • 简化计算,把像素点的梯度方向离散为8个方向
  1. 应用双阈值检测来确定真是的和潜在的边缘
  • 大于上边界,处理为边界
  • 在上下边界之间,如果连有边界,则保留
  • 小于下边界,舍弃
  1. 通过抑制鼓励的弱边缘完成边缘检测
img = cv2.imread('car.jpg', cv2.IMREAD_GRAYSCALE)# minval 和 maxval
v1 = cv2.Canny(img, 30, 100)
v2 = cv2.Canny(img, 50, 150)plt.figure(figsize=(20,25))plt.subplot(121)
plt.imshow(v1, cmap='gray')plt.subplot(122)
plt.imshow(v2, cmap='gray')plt.show()

opencv边缘检测.png

三、图像金字塔

高斯金字塔

  1. 向下采样,缩小

    将Gi与高斯内核卷积

    去除偶数行和列

  2. 向上采样,放大

    图像在每个方向扩大为原来的两倍,新增的行列0填充

    使用高斯内核与放大后的图像卷积,获得近似值

img = cv2.imread('jerry.jpg')
up = cv2.pyrUp(img)
down = cv2.pyrDown(img)plt.figure(figsize=(20,15))plt.subplot(131)
plt.imshow(cv2.cvtColor(img, cv2.COLOR_BGR2RGB))plt.subplot(132)
plt.imshow(cv2.cvtColor(up, cv2.COLOR_BGR2RGB))plt.subplot(133)
plt.imshow(cv2.cvtColor(down, cv2.COLOR_BGR2RGB))plt.show()

虽然看着图片大小一样,看坐标轴上可以看出来实际大小是不一样的,清晰的也略有差异

opencv高斯金字塔.png

拉普拉斯金字塔

每一层都是Li+1 = Gi - pyrUp(pyrDown(Gi))

down_up = cv2.resize(cv2.pyrUp(cv2.pyrDown(img)),(500, 635))
res = img - down_upplt.imshow(cv2.cvtColor(res, cv2.COLOR_BGR2RGB))
plt.show()

opencv拉普拉斯金字塔.png

四、轮廓检测

轮廓检测函数

cv2.findContours(img,mode,method)

mode:轮廓检索模式

  • RETR_EXTERNAL:只检索最外面的轮廓
  • RETR_LIST:检索所有轮廓,保存到一条链表
  • RETR_CCOMP:检索所有轮廓,组织为两层,定策是各部分的外部边界,第二层是空洞的边界
  • RETR_TREE:检索所有的轮廓,并重构嵌套轮廓的整个层次

method:轮廓逼近方法

  • CHAINAPPROXNONE:以Freeman链码的方式输出轮廓,所有其它方法输出多边形
  • CHAINAPPROXSIMPLE:压缩水平的、垂直的和斜的部分,只保留终点

转换图片为二值图像

# 二值图像准确率更高
img = cv2.imread('contours.jpg')
img_gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
# 转为二值图像
ret,thresh = cv2.threshold(img_gray, 127, 255, cv2.THRESH_BINARY)plt.imshow(thresh,'gray')
plt.show()

opencv轮廓检测二值图像.png

绘制轮廓

# 二值图像,轮廓信息,层级
binary, contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE)
# 使用原图会导致原图改变
img_copy = img.copy()
# 绘制全部轮廓,BGR,线宽
res = cv2.drawContours(img_copy, contours, -1, (0,0,255),2)plt.imshow(cv2.cvtColor(res, cv2.COLOR_BGR2RGB))
plt.show()

opencv绘制轮廓.png

轮廓特征

# 拿出星形的外圈轮廓
cnt = contours[0]print('星形外圈包围的面积为',cv2.contourArea(cnt))
print('星形外圈周长为',cv2.arcLength(cnt,True))

轮廓近似

原轮廓

img = cv2.imread('irregular.jpg')
img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
ret, thresh = cv2.threshold(img_gray, 127,255,cv2.THRESH_BINARY)binary, contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE)
cnt = contours[0]
img_copy = img.copy()
res = cv2.drawContours(img_copy, [cnt], 0, (0,0,255),2)plt.imshow(cv2.cvtColor(res, cv2.COLOR_BGR2RGB))
plt.show()

opencv不规则轮廓.png

有时我们不需要这么精准的轮廓

# 0.1倍的周长作为阈值
epsilon = 0.1 * cv2.arcLength(cnt, True)
approx = cv2.approxPolyDP(cnt, epsilon, True)img_copy = img.copy()
res = cv2.drawContours(img_copy, [approx], -1, (0,0,255),2)plt.imshow(cv2.cvtColor(res, cv2.COLOR_BGR2RGB))
plt.show()

opencv近似轮廓.png

轮廓外接图形

外接矩形

img = cv2.imread('contours.jpg')
img_gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
ret,thresh = cv2.threshold(img_gray, 127, 255, cv2.THRESH_BINARY)binary, contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE)
cnt = contours[0]
# 得到四条边
x,y,w,h = cv2.boundingRect(cnt)
img_copy = img.copy()
res = cv2.rectangle(img_copy, (x, y), (x + w, y + h), (0,255,0), 2)plt.imshow(cv2.cvtColor(res, cv2.COLOR_BGR2RGB))
plt.show()

opencv外接矩形.png

外接圆

(x, y), radius = cv2.minEnclosingCircle(cnt)
center = (int(x), int(y))
radius = int(radius)
res = cv2.circle(img, center, radius, (0,255,0),2)plt.imshow(cv2.cvtColor(res, cv2.COLOR_BGR2RGB))
plt.show()

opencv外接圆.png

五、模板匹配

就是从大图像中找出匹配的目标图像

img = cv2.imread('car.jpg')
template = cv2.imread('wheel.jpg')
h,w = template.shape[:2]
# 常用方法
methods={'cv2.TM_CCOEFF','cv2.TM_CCOEFF_NORMED','cv2.TM_CCORR','cv2.TM_CCORR_NORMED','cv2.TM_SQDIFF','cv2.TM_SQDIFF_NORMED'}for m in methods:img2 = img.copy()# 获得匹配方法的真值method = eval(m)# 进行匹配res = cv2.matchTemplate(img,template, method)# 获得匹配的最高最低得分值及其位置min_val, max_val, min_loc, max_loc = cv2.minMaxLoc(res)# 如果是平方差匹配或者归一化平方差匹配,取最小值if method in [cv2.TM_SQDIFF, cv2.TM_SQDIFF_NORMED]:top_left = min_locelse: top_left = max_locbottom_right = (top_left[0] + w, top_left[1] + h)# 绘制矩形cv2.rectangle(img2, top_left, bottom_right, 255, 2)plt.subplot(121)plt.imshow(res, 'gray')plt.xticks([])plt.yticks([])plt.subplot(122)plt.imshow(img2, 'gray')plt.xticks([])plt.yticks([])plt.suptitle(m)plt.show()

图片太长了,这里只展示一部分,从结果中可以看出, 带归一化的方法比不带归一化的方法要更加精准

opencv模板匹配.png

六、图像直方图

直方图直观的表示图片中某个(或某组)像素值的像素点个数

直方图函数

cv2.calcHist(images,channels,mask,histSize,ranges)

  • images:输入图像
  • channels:012对应BGR
  • mask:掩模图像,统计整幅图像就设为None。
  • histSize:BIN的数量(一个柱表示的像素范围)
  • ranges:像素值范围
img = cv2.imread('cat.jpg',cv2.IMREAD_GRAYSCALE)
hist = cv2.calcHist([img],[0],None,[256],[0,256])plt.hist(img.ravel(),256)
plt.show()

opencv直方图.png

三通道直方图

img = cv2.imread('cat.jpg')
color = ('b','g','r')
for i, col in enumerate(color):histr = cv2.calcHist([img],[i],None,[256],[0,256])plt.plot(histr, color=col)plt.xlim([0,256])
plt.show()

opencv三通道直方图.png

直方图均衡化

img = cv2.imread('cat.jpg',cv2.IMREAD_GRAYSCALE)
equ = cv2.equalizeHist(img)
plt.hist(equ.ravel(), 256)
plt.show()plt.subplot(121)
plt.imshow(img, 'gray')
plt.subplot(122)
plt.imshow(equ, 'gray')
plt.show()

opencv直方图均衡化.png

opencv均衡化对比.png

自适应均衡化

clahe = cv2.createCLAHE(clipLimit=2.0, tileGridSize=(8,8))
res_clahe = clahe.apply(img)plt.subplot(121)
plt.imshow(img, 'gray')plt.subplot(122)
plt.imshow(res_clahe, 'gray')plt.show()

opencv自适应均衡化.png

七、傅里叶变换

img = cv2.imread('cat.jpg', cv2.IMREAD_GRAYSCALE)
img_float32 = np.float32(img)dft = cv2.dft(img_float32, flags=cv2.DFT_COMPLEX_OUTPUT)
dft_shift = np.fft.fftshift(dft)# 转为灰度图表示形式
magnitude_spectrum = 20 * np.log(cv2.magnitude(dft_shift[:,:,0], dft_shift[:,:,1]))plt.subplot(121)
plt.imshow(img, 'gray')
plt.title('input')plt.subplot(122)
plt.imshow(magnitude_spectrum, 'gray')
plt.title('output')plt.show()

opencv傅里叶变换特征图.png

拿到特征图后可以使用低通滤波使图像边缘模糊,或者使用高通滤波加强图像边缘

img = cv2.imread('cat.jpg', cv2.IMREAD_GRAYSCALE)
img_float32 = np.float32(img)dft = cv2.dft(img_float32, flags=cv2.DFT_COMPLEX_OUTPUT)
dft_shift = np.fft.fftshift(dft)rows,cols = img.shape
# 中心
crow,ccol = int(rows/2), int(cols/2)# 低通滤波
mask = np.zeros((rows,cols,2), np.uint8)
mask[crow-30:crow+30, ccol-30:ccol+30] = 1
fshift = dft_shift * mask# idft
f_ishift = np.fft.ifftshift(fshift)
img_back = cv2.idft(f_ishift)
img_back = cv2.magnitude(img_back[:,:,0], img_back[:,:,1])plt.subplot(121)
plt.imshow(img, 'gray')
plt.title('input')plt.subplot(122)
plt.imshow(img_back, 'gray')
plt.title('output')plt.show()img = cv2.imread('cat.jpg', cv2.IMREAD_GRAYSCALE)
img_float32 = np.float32(img)dft = cv2.dft(img_float32, flags=cv2.DFT_COMPLEX_OUTPUT)
dft_shift = np.fft.fftshift(dft)rows,cols = img.shape
# 中心
crow,ccol = int(rows/2), int(cols/2)# 高通滤波
mask = np.ones((rows,cols,2), np.uint8)
mask[crow-30:crow+30, ccol-30:ccol+30] = 0
fshift = dft_shift * mask
# idft
f_ishift = np.fft.ifftshift(fshift)
img_back = cv2.idft(f_ishift)
img_back = cv2.magnitude(img_back[:,:,0], img_back[:,:,1])plt.subplot(121)
plt.imshow(img, 'gray')
plt.title('input')plt.subplot(122)
plt.imshow(img_back, 'gray')
plt.title('output')plt.show()

opencv滤波.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/11683.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

域控安全 ----> Ntds.dit文件抓取

大家还记得内网渗透的初衷吗??? 找到域馆,拿下域控!! 拿下了域控就是拿下了整个域!! 但是大家知道拿下域环境之后应该怎么操作吗(灵魂拷问)??? …

GCP谷歌云有什么数据库类型,该怎么选择

GCP谷歌云提供的数据库类型主要包括: 关系型数据库:这类数据库适用于结构化数据,通常用于数据结构不经常发生变化的场合。在GCP中,关系型数据库选项包括Cloud SQL和Cloud Spanner。Cloud SQL提供托管的MySQL、PostgreSQL和SQL Se…

提升文本到图像模型的空间一致性:SPRIGHT数据集与训练技术的新进展

当前的T2I模型,如Stable Diffusion和DALL-E,虽然在生成高分辨率、逼真图像方面取得了成功,但在空间一致性方面存在不足。这些模型往往无法精确地按照文本提示中描述的空间关系来生成图像。为了解决这一问题,研究人员进行了深入分析…

vue + element-plus 开发中遇到的问题

1.问题之路由守卫 初写路由守卫,对于next()的理解不是很透彻,就想着都放行,不然看不到效果,结果控制台出现了警告,想着报黄的问题就不是问题,但仔细一看发现他说,如果再生产阶段就会失败&#x…

STM32(开篇总结)

STM32介绍 STM32是意法半导体公司基于ARM Cortex-M内核开发的32位微控制器 STM32常应用在嵌入式领域,如智能车、无人机、机器人、无线通信、物联网、工业控制、娱乐电子产品等 STM32功能强大、性能优异片上资源丰富、功耗低,是一款经典的嵌入式微控制器…

数据可视化(十二):Pandas太阳黑子数据、图像处理——离散极值、核密度、拟合曲线、奇异值分解等高级操作

Tips:"分享是快乐的源泉💧,在我的博客里,不仅有知识的海洋🌊,还有满满的正能量加持💪,快来和我一起分享这份快乐吧😊! 喜欢我的博客的话,记得…

SpringSecurity的核心原理使用总结

1. SpringSecurity的核心原理 对于最原始Servlet请求处理的层次结构 客户端->过滤器链->Servlet 对于在SpringMVC中处理请求的层次结构 如何让Filter与Spring建立连接呢? 因此它增加了一个DelegatingFilterProxy 它是SpringMVC提供的的Filter,它内部代理了一个原生的F…

Spring框架概述

目录 1. Spring框架的起源 2. Spring框架的构成 3. Spring的发展历程 4. Spring的开发环境 4.1. Maven安装与配置 (1)Maven的下载与安装 (2)配置Maven的环境变量 (3)本地仓库的配置 (4…

景联文科技:用高质量数据采集标注赋能无人机技术,引领无人机迈入新纪元!

随着无人机技术的不断发展与革新,它已成为现代社会中一个前景无限的科技领域。 无人机应用领域 边境巡逻与安防:边境管理部门利用无人机监控边境线,防止非法越境和其他安全威胁,同时也能监控地面安保人员的工作状态和行动路线。 …

JVM的垃圾回收算法有哪些?从可达性分析算法开始,深入解读三大核心垃圾回收算法

导航: 【Java笔记踩坑汇总】Java基础JavaWebSSMSpringBootSpringCloud瑞吉外卖/黑马旅游/谷粒商城/学成在线设计模式面试题汇总性能调优/架构设计源码-CSDN博客 目录 一、概念准备 1.1 GC Roots 1.2 可达性分析算法 1.3 非可达对象被回收过程中的两次标记 1.4…

vue从入门到精通(一):初始Vue

一,Vue是什么 Vue (读音 /vjuː/,类似于 view) 是一套用于构建用户界面的渐进式框架。Vue 被设计为可以自底向上逐层应用。Vue 的核心库只关注视图层,不仅易于上手,还便于与第三方库或既有项目整合。另一方面,当与现代…

质量保障之精准测试!

一、背景与概念 随着软件测试行业的长足发展,测试理念、技术都在发生着日新月异的变化。因此一套完整的自动化测试用例对于每个软件公司都是不可或缺的,然而虽然有如此规模宏大的自动化案例集资源投入,同时也有大量人力的投入,但…

虚拟仿真云平台在教育应用中的优势和意义

虚拟仿真云实验教学平台作为一种新型的教学方法,近年来在高校教育中得到了十分广泛的应用。它通过模拟真实的实验场景和实验操作,让学生在计算机上进行实验操作和数据处理,为学生提供了更加便捷、可靠、有效的实验学习环境。本文,…

Python如何绘制直流电机开闭环特性曲线?matplotlib

import matplotlib.pyplot as plt from pylab import mplmpl.rcParams[font.sans-serif] [FangSong] # 指定默认字体 mpl.rcParams[axes.unicode_minus] False # 解决保存图像是负号-显示为方块的问题# 数据集1 n1 [1206, 1174, 1141, 1116, 1037, 986] Id1 [0.505, 0.55…

【多模态】30、GPT4V_OCR | GPT4V 在 OCR 数据集上效果测评

文章目录 一、背景二、测评2.1 场景文本识别2.2 手写文本识别2.3 手写数学公式识别2.4 图表结构识别(不考虑单元格中的文本内容)2.5 从内容丰富的文档中抽取信息 三、讨论 论文:EXPLORING OCR CAPABILITIES OF GPT-4V(ISION) : A QUANTITATIV…

centos7.6安装mysql

博客主页:花果山~程序猿-CSDN博客 文章分栏:MySQL之旅_花果山~程序猿的博客-CSDN博客 关注我一起学习,一起进步,一起探索编程的无限可能吧!让我们一起努力,一起成长! 目录 1.在网页中寻找mysql…

【QT】QT环境搭建

本专栏内容为:QT学习专栏 通过本专栏的深入学习,你可以了解并掌握QT。 💓博主csdn个人主页:小小unicorn ⏩专栏分类:QT 🚚代码仓库:小小unicorn的代码仓库🚚 🌹&#x1f…

WordPress 管理员密码重置方法汇总

最近明月碰到一个 WordPress 站长求助咨询,说是自己 WordPress 站点的管理员密码被恶意篡改了,对 WordPress 了解的都知道这一般都是恶意代码造成的,问题大多出在使用了所谓的破解版、去授权版的插件或者主题被植入了恶意代码、后门木马。明月…

洗地机哪个牌子好性价比高又实惠?高性价比洗地机推荐【避坑指南】

洗地机是一种智能清洁家具,具有强大的清洁能力,可快速有效地清洁各种地面污渍,操作简便,省时省力。其一键操作功能使其易于上手,无需频繁清洗拖布和更换水,大大提高了清洁效率。部分高端洗地机还具备智能感…

全国防灾减灾日主题活动投稿我可算找对了投稿方法

作为一名社区公众人员,我深知对外信息宣传的重要性。特别是在全国防灾减灾日这样的特殊时刻,我们不仅要向居民普及防灾减灾知识,还要通过媒体将社区的活动和成果展示给更多人。然而,在投稿的过程中,我最初却遭遇了诸多挑战。 起初,我采用传统的邮箱投稿方式,将精心撰写的稿件发…