[Python从零到壹] 三十四.OpenCV入门详解——显示读取修改及保存图像

网友投稿 995 2022-05-29

该系列文章主要讲解Python OpenCV图像处理和图像识别知识,前期主要讲解图像处理基础知识、OpenCV基础用法、常用图像绘制方法、图像几何变换等,中期讲解图像处理的各种运算,包括图像点运算、形态学处理、图像锐化、图像增强、图像平滑等,后期研究图像识别、图像分割、图像分类、图像特效处理以及图像处理相关应用。

上一篇文章介绍了图像处理基础知识,这篇文章将详细讲解OpenCV入门知识,包括OpenCV常见数据类型、显示图像、读取像素、修改像素、创建图像、复制图像、保存图像等内容。希望文章对您有所帮助,如果有不足之处,还请海涵。接下来,让我们开启整个系列的学习吧!

文章目录

一.什么是图像处理

二.图像处理基础

三.Python语言

四.OpenCV安装和基础

五.总结

-:

https://github.com/eastmountyxz/Python-zero2one

前文赏析:

第一部分 基础语法

[Python从零到壹] 一.为什么我们要学Python及基础语法详解

[Python从零到壹] 二.语法基础之条件语句、循环语句和函数

[Python从零到壹] 三.语法基础之文件操作、CSV文件读写及面向对象

第二部分 网络爬虫

[Python从零到壹] 四.网络爬虫之入门基础及正则表达式抓取博客案例

[Python从零到壹] 五.网络爬虫之BeautifulSoup基础语法万字详解

[Python从零到壹] 六.网络爬虫之BeautifulSoup爬取豆瓣TOP250电影详解

[Python从零到壹] 七.网络爬虫之Requests爬取豆瓣电影TOP250及CSV存储

[Python从零到壹] 八.数据库之MySQL基础知识及操作万字详解

[Python从零到壹] 九.网络爬虫之Selenium基础技术万字详解

[Python从零到壹] 十.Selenium爬取在线百科知识万字详解(NLP语料构造必备技能)

第三部分 数据分析和机器学习

[Python从零到壹] 十一.数据分析之Numpy、Pandas、Matplotlib和Sklearn入门知识万字详解

[Python从零到壹] 十二.机器学习之回归分析万字总结

[Python从零到壹] 十三.机器学习之聚类分析万字总结全网首发(K-Means、BIRCH、层次聚类、树状聚类)

[Python从零到壹] 十四.机器学习之分类算法五万字总结全网首发(决策树、KNN、SVM、分类对比实验)

[Python从零到壹] 十五.文本挖掘之数据预处理、Jieba工具和文本聚类万字详解

[Python从零到壹] 十六.文本挖掘之词云热点与LDA主题分布分析万字详解

[Python从零到壹] 十七.可视化分析之Matplotlib、Pandas、Echarts入门万字详解

[Python从零到壹] 十八.可视化分析之Basemap地图包入门详解

[Python从零到壹] 十九.可视化分析之热力图和箱图绘制及应用详解

[Python从零到壹] 二十.可视化分析之Seaborn绘图万字详解

[Python从零到壹] 二十一.可视化分析之Pyechart绘图万字详解

[Python从零到壹] 二十二.可视化分析之OpenGL绘图万字详解

[Python从零到壹] 二十三.十大机器学习算法之决策树分类分析详解(1)

[Python从零到壹] 二十四.十大机器学习算法之KMeans聚类分析详解(2)

[Python从零到壹] 二十五.十大机器学习算法之KNN算法及图像分类详解(3)

[Python从零到壹] 二十六.十大机器学习算法之朴素贝叶斯算法及文本分类详解(4)

[Python从零到壹] 二十七.十大机器学习算法之线性回归算法分析详解(5)

[Python从零到壹] 二十八.十大机器学习算法之SVM算法分析详解(6)

[Python从零到壹] 二十九.十大机器学习算法之随机森林算法分析详解(7)

[Python从零到壹] 三十.十大机器学习算法之逻辑回归算法及恶意请求检测应用详解(8)

[Python从零到壹] 三十一.十大机器学习算法之Boosting和AdaBoost应用详解(9)

[Python从零到壹] 三十二.十大机器学习算法之层次聚类和树状图聚类应用详解(10)

第四部分 Python图像处理基础

[Python从零到壹] 三十三.图像处理基础篇之什么是图像处理和OpenCV配置

[Python从零到壹] 三十四.OpenCV入门详解——显示读取修改及保存图像

第五部分 Python图像运算和图像增强

第六部分 Python图像识别和图像处理经典案例

第七部分 NLP与文本挖掘

第八部分 人工智能入门知识

第九部分 网络攻防与AI安全

第十部分 知识图谱构建实战

扩展部分 人工智能高级案例

一.OpenCV常见数据类型

OpenCV是一个轻量级高效的跨平台计算机视觉库,实现了图像处理和计算机视觉方面的多种通用算法。所谓的图像可以理解为一个数组,图像处理就是对数组的处理。首先,本文将介绍OpenCV中常见的数据类型,包括点Point类、颜色Scalar类、尺寸Size类、矩形Rect类、矩阵Mat类[1-2]。

1.点Point

表示二维坐标系中的点,含x和y。其示例如下:

#OpenCV示例 Point p; p.x=1, p.y=2; Point p=Point(1, 2); #Python示例 points_list = [(160, 160), (136, 160)]

2.颜色Scalar

包含四个元素的数组,设置像素值RGB三通道,第四个参数可忽略。其示例如下:

#OpenCV示例 BGR三分量 Scalar(b, g, r); #Python示例 (0, 0, 255)

3.尺寸Size

它和Point相似,主要成员包括height和width。其示例如下:

#OpenCV示例 Size(5, 5); Size_(_Tp _width, _Tp _height); #Python示例 width, height = img.shape

4.矩形Rect

Rect类称为矩形类,包含Point类的成员x和y(代表矩形左上角的坐标)和Size类的成员width和height(代表矩形的大小)。其示例如下:

#OpenCV示例 Rect rect = rect1 & rect2; #求两矩形交集 Rect rect = rect1 | rect2; #求两矩形并集 Rect rectShift = rect + point; #矩形平移 Rect rect = rect1 + size; #矩形缩放 #Python示例 cv2.rectangle(img, (20,20), (150,250), (255,0,0), 2)

5.矩阵Mat

通用的矩阵类,用来创建和操作多维矩阵。其示例如下:

#OpenCV示例 Mat M(3,2, CV_8UC3, Scalar(0,0,255)); #Python示例 np.zeros((256,256,3), np.uint8)

二.OpenCV读取与显示图像

在OpenCV2中,图像的读取和显示是最简单的两句代码,它们通过imread()和imshow()函数实现[3]。OpenCV读取图像的imread()函数原型如下,它将从指定的文件加载图像并返回矩阵,如果无法读取图像(因为缺少文件、权限不正确、格式不支持或图像无效等),则返回空矩阵(Mat::data==NULL)。

retval = imread(filename[, flags])

– filename表示需要载入的图片路径名,其支持Windows位图、JPEG文件、PNG图片、便携文件格式、Sun rasters光栅文件、TIFF文件、HDR文件等。

flags为int类型,表示载入标识,它指定一个加载图像的颜色类型,默认值为1。其中cv2.IMREAD_UNCHANGED表示读入完整图像或图像不可变,包括alpha通道;cv2.IMREAD_GRAYSCALE表示读入灰度图像;cv2.IMREAD_COLOR表示读入彩色图像,默认参数,忽略alpha通道。

OpenCV中显示图像调用imshow()函数,它将在指定窗口中显示一幅图像,窗口会自动调整为图像大小,其原型如下所示:

imshow(winname, mat)

– winname表示窗口的名称

– mat表示要显示的图像

下面是第一个示例程序,主要用于读取和加载经典的“Lena”图像。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 #读取图片 img = cv2.imread("Lena.png") #显示图像 cv2.imshow("Demo", img) #等待显示 cv2.waitKey(0) cv2.destroyAllWindows()

输出结果如图2-1所示:

需要注意,在图像显示过程中,如果代码中没有waitKey(0)函数,其运行结果可能会出现错误,加载一幅灰色的图像,如图2-2所示。

因此,在显示图像过程中,通常还会调用两个操作窗口的函数,它们分别是waitKey()和destroyAllWindows()。

retval = waitKey([, delay])

– 键盘绑定函数,共一个参数delay,表示等待的毫秒数,看键盘是否有输入,返回值为ASCII值。如果其参数为0,则表示无限期的等待键盘输入;参数大于0表示等待delay毫秒;参数小于0表示等待键盘单击。

destroyAllWindows()

– 该函数可以轻易删除所有建立的窗口。如果你想删除特定的窗口可以使用 cv2.destroyWindow(),并在括号内输入要删除的窗口名。

同时,可以设置加载图像后无限期等待,直到输入指定的按键才退出窗口,如下面的代码需要输入ESC才退出。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 #读取图片 img = cv2.imread("Lena.png") #显示图像 cv2.imshow("Demo", img) #无限期等待输入 k=cv2.waitKey(0) #如果输入ESC按键退出 if k==27: cv2.destroyAllWindows()

此外,在对比实验中,我们通常需要显示多张图片,此时可以调用NumPy和Matplotlib库辅助完成[4],具体实现过程如下所示。

NumPy(Numeric Python)是Python提供的数值计算扩展包,拥有高效的处理函数和数值编程工具,主要用于科学计算,如矩阵数据类型、线性代数、矢量处理等。

Matplotlib是Python强大的数据可视化工具和2D绘图库,常用于创建海量类型的2D图表和一些基本的3D图表,类似于MATLAB和R语言。Matplotlib提供了一整套和Matlab相似的命令API,十分适合交互式地进行制图,而且也可以方便地将它作为绘图控件,嵌入GUI应用程序中。Matplotlib是一名神经生物学家John D. Hunter博士于2007年创建,函数设计上参考了Matlab,现在在Python的各个科学计算领域都得到了广泛应用。

该程序是调用cv2.imread()函数分别读取四张图片,并转换为RGB颜色空间,接着通过for循环分别设置各子图对应的图像、标题及坐标轴名称,其中plt.subplot(2,2)表示生成2×2张子图。

# -*- coding: utf-8 -*- # By:Eastmount import cv2 import numpy as np import matplotlib.pyplot as plt #读取图像 img1 = cv2.imread('lena.png') img1 = cv2.cvtColor(img1, cv2.COLOR_BGR2RGB) img2 = cv2.imread('xluo.png') img2 = cv2.cvtColor(img2, cv2.COLOR_BGR2RGB) img3 = cv2.imread('flower.png') img3 = cv2.cvtColor(img3, cv2.COLOR_BGR2RGB) img4 = cv2.imread('huawei.png') img4 = cv2.cvtColor(img4, cv2.COLOR_BGR2RGB) #显示四张图像 titles = ['lena', 'people', 'flower', 'huawei'] images = [img1, img2, img3, img4] for i in range(4): plt.subplot(2, 2, i+1), plt.imshow(images[i], 'gray') plt.title(titles[i]) plt.xticks([]),plt.yticks([]) plt.show()

输出如图2-3所示,它显示了四幅图像。在图像处理对比中,同时对比多种算法的处理效果是非常重要的手段之一。

三.OpenCV像素处理

OpenCV中读取图像的像素值可以直接通过遍历图像的位置实现,如果是灰度图像则返回其灰度值,如果是彩色图像则返回蓝色(B)、绿色(G)、红色(G)三个分量值。其示例如下:

灰度图像:返回值 = 图像[位置参数]

示例:test=img[88,42]

彩色图像:返回值 = 图像[位置元素, 0 | 1 | 2 ]获取BGR三个通道像素

示例:blue=img[88,142,0] green=img[88,142,1] red=img[88,142,2]

当需要修改图像中的像素时,则定位指定像素并直接赋新像素值即可,彩色图像需要依次给三个分量赋值。如下列代码所示。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 #读取图片 img = cv2.imread("Lena.png") #读取像素 test = img[88,142] print("读取的像素值:", test) #修改像素 img[88,142] = [255, 255, 255] print("修改后的像素值:", test) #分别获取BGR通道像素 blue = img[88,142,0] print("蓝色分量", blue) green = img[88,142,1] print("绿色分量", green) red = img[88,142,2] print("红色分量", red) #显示图像 cv2.imshow("Demo", img) #等待显示 cv2.waitKey(0) cv2.destroyAllWindows()

读取的像素值及修改后的像素值结果如图2-4所示。

下面代码是将100到200行、150到250列的像素区域设置为白色的效果。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 #读取图片 img = cv2.imread("Lena.png") #该区域设置为白色 img[100:200, 150:250] = [255,255,255] #显示图像 cv2.imshow("Demo", img) #等待显示 cv2.waitKey(0) cv2.destroyAllWindows()

图2-5是最终显示的效果图,它将img[100:200, 150:250] 区域显示为白色。

四.NumPy像素处理

前面是直接读取和修改图像像素的方法,下面讲解通过NumPy库读取像素和修改像素的方法。NumPy是Python提供的数值计算扩展包,拥有高效的处理函数和数值编程工具,Array是NumPy库中最基础的数据结构,表示数组。NumPy可以很方便地创建各种不同类型的多维数组,并且执行一些基础操作。

在图像处理中,NumPy读取像素调用item()函数实现,修改像素调用itemset()实现,其原型如下所示[5]。使用Numpy进行像素读取,调用方式如下:

返回值 = 图像.item(位置参数)

例如:blue = img.item(78, 100, 0)

使用Numpy的itemset函数修改像素,调用方式如下:

图像.itemset(位置, 新值)

例如:img.itemset((88,99), 255)

最终实现代码如下所示。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 import numpy #读取图片 img = cv2.imread("Lena.png") print(type(img)) #Numpy读取像素 print(img.item(78, 100, 0)) print(img.item(78, 100, 1)) print(img.item(78, 100, 2)) #Numpy修改像素 img.itemset((78, 100, 0), 100) img.itemset((78, 100, 1), 100) img.itemset((78, 100, 2), 100) print(img.item(78, 100, 0)) print(img.item(78, 100, 1)) print(img.item(78, 100, 2))

输出结果如下所示,原始图像BGR像素值为88、84、196,修改后的像素值为100、100、100。

88 84 196 100 100 100

[Python从零到壹] 三十四.OpenCV入门详解——显示读取修改及保存图像

五.OpenCV创建图像

由于在OpenCV2中没有CreateImage函数,如果需要创建图像,则需要使用Numpy库函数实现。如下述代码,调用np.zeros()函数创建空图像,创建的新图像使用Numpy数组的属性来表示图像的尺寸和通道信息,其中参数img.shape表示原始图像的形状,np.uint8表示类型。

emptyImage = np.zeros(img.shape, np.uint8)

例如img.shape为(500, 300, 3),它表示500×300像素的图像,3表示这是一个RGB图像。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 import numpy as np #读取图片 img = cv2.imread("Lena.png") #创建空图像 emptyImage = np.zeros(img.shape, np.uint8) #显示图像 cv2.imshow("Demo", emptyImage) #等待显示 cv2.waitKey(0) cv2.destroyAllWindows()

显示结果如图2-6所示,这是一幅新创建的“空白”图像。

六.OpenCV复制图像

复制原有图像来获取一幅新图像,可以调用copy()函数实现。

emptyImage2 = img.copy()

下述代码实现了图像的创建和复制功能。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 import numpy as np #读取图片 img = cv2.imread("Lena.png") #创建空图像 emptyImage = np.zeros(img.shape, np.uint8) #复制图像 emptyImage2 = img.copy() #显示图像 cv2.imshow("Demo1", img) cv2.imshow("Demo2", emptyImage) cv2.imshow("Demo3", emptyImage2) #等待显示 cv2.waitKey(0) cv2.destroyAllWindows()

最终输出结果如图2-7所示,Demo1表示原始图像,Demo2表示创建的空白图像,Demo3表示复制的图像。

七.OpenCV保存图像

在OpenCV中,输出图像到文件使用的函数为imwrite(),其函数原型如下:

retval = imwrite(filename, img[, params])

– filename表示要保存的路径及文件名

– img表示图像矩阵

– params表示特定格式保存的参数编码,默认值为空。对于JPEG图片,该参数(cv2.IMWRITE_JPEG_QUALITY)表示图像的质量,用0-100的整数表示,默认值为95。对于PNG图片,该参数(cv2.IMWRITE_PNG_COMPRESSION)表示的是压缩级别,从0到9,压缩级别越高,图像尺寸越小,默认级别为3。对于PPM、PGM、PBM图片,该参数表示一个二进制格式的标志(cv2.IMWRITE_PXM_BINARY)[2]。注意,该类型为Long,必须转换成int。

下面是一个调用imwrite()函数输出图像到指定的文件的代码。

# -*- coding:utf-8 -*- # By:Eastmount import cv2 import numpy as np #读取图像 img = cv2.imread("Lena.png") #显示图像 cv2.imshow("Demo", img) #保存图像 cv2.imwrite("dst1.jpg", img, [int(cv2.IMWRITE_JPEG_QUALITY), 5]) cv2.imwrite("dst2.jpg", img, [int(cv2.IMWRITE_JPEG_QUALITY), 100]) cv2.imwrite("dst3.png", img, [int(cv2.IMWRITE_PNG_COMPRESSION), 0]) cv2.imwrite("dst4.png", img, [int(cv2.IMWRITE_PNG_COMPRESSION), 9]) #等待显示 cv2.waitKey(0) cv2.destroyAllWindows()

原始图像“Lena.jpg”为222KB,调用imwrite()函数输出保存的图像共四张,如图2-8所示,其中“dst1.jpg”被压缩,大小为4.90KB,“dst2.jpg”图像大小为99.1KB,“dst3.png”大小为499KB,“dst4.png”大小为193KB。

八.总结

写到这里,这篇文章就介绍结束。本文详细介绍了OpenCV图像处理的基础用法,包括图像读取、显示、像素处理、创建、复制、写入和保存。通过这篇文章,初学者将学会基本的图像处理操作,代码比较简单,但希望大家一定要自己动手实现所有代码和案例,只有不断实践才能提升。

感谢在求学路上的同行者,不负遇见,勿忘初心。

感恩能与大家在华为云遇见!

希望能与大家一起在华为云社区共同成长,原文地址:https://blog.csdn.net/Eastmount/article/details/122654530

(By:娜璋之家 Eastmount 2022-02-28 夜于武汉)

参考文献:

[1] 冈萨雷斯. 数字图像处理(第3版)[M]. 北京:电子工业出版社, 2013.

[2] 阮秋琦. 数字图像处理学(第3版)[M]. 北京:电子工业出版社,2008.

[3] Eastmount. [Python图像处理] 一.图像处理基础知识及OpenCV入门函数[EB/OL]. (2018-08-16). https://blog.csdn.net/Eastmount/article/details/81748802.

[4] 杨秀璋, 颜娜. Python网络数据爬取及分析从入门到精通(分析篇)[M]. 北京:北京航天航空大学出版社, 2018.

[5] Eastmount. [Python图像处理] 二.OpenCV+Numpy库读取与修改像素[EB/OL]. (2018-08-28). https://blog.csdn.net/eastmount/article/details/82120114.

OpenCV Python

版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:Linux系统常用命令,指令详解及案例
下一篇:Java面向对象知识点拆分(二)
相关文章