我是靠谱客的博主 冷酷自行车,最近开发中收集的这篇文章主要介绍OpenCV常用操作1 OpenCV入门基础2 图像处理基础3 图像运算4 图像几何变换5 图像平滑处理,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

原创:杨其泓

1 OpenCV入门基础

1.1 OpenCV简介

OpenCV的全称是Open Source Computer Vision Library,是一个跨平台的计算机视觉库。OpenCV是由英特尔公司发起并参与开发,以BSD许可证授权发行,可以在商业和研究领域中免费使用。OpenCV可用于开发实时的图像处理、计算机视觉以及模式识别程序。OpenCV-Python是OpenCV的Python API,集成了Python语言和C++语言的最优特征,致力于支持Python解决计算机视觉问题。

1.2 Python安装OpenCV

在Python中安装OpenCV十分便捷,可以直接使用:pip install opencv-pythonconda insatll opencv-python即可。

注:默认安装最新版,如有特定版本需求,可使用pip install opencv-python==4.1.2

在成功安装OpenCV后,可以在Python编译器中键入如下内容,查看是否安装成功:

import cv2
print(cv2.__version__)

1.3 图片的读取、显示与保存

  1. 图像读取

使用OpenCV读取图片文件,可以使用函数cv2.imread(filepath, flags),例如:

image=cv2.imread('test.jpg')

该函数共接收两个输入,即要读入图片的完整路径和读入图片的方式,常用方式包括以下三种

  • cv2.IMREAD_COLOR:默认参数,读入一副彩色图片,忽略alpha通道
  • cv2.IMREAD_GRAYSCALE:读入灰度图片
  • cv2.IMREAD_UNCHANGED:顾名思义,读入完整图片,包括alpha通道

OpenCV读取图片后返回的是一个numpy数组,对于彩色图像,数组为三维数组,其形状(shape)为(图像高,图像宽,3),其中3代表图片的RGB三个通道,由于OpenCV在存储彩色图像时,默认通道顺序为BGR,在进行图像处理时要注意不要使用错误的通道顺序。

  1. 图像显示

使用OpenCV显示图片文件,可以使用函数cv2.imshow(wname, img),例如:

cv2.imshow('Test_image', image)

在多数时候,我们会将上述API搭配cv2.waitKey()cv2.destroyAllWindows()使用,waitKey顾名思义,就是等待键盘键入,而destroyAllWindows就是关闭所有已经显示的窗口,搭配这两个API后即可实现:显示一张图片,并在键盘键入任意值后关闭图片的效果。

下面就是使用OpenCV读入图片并展示的样例代码:

import cv2
image_BGR = cv2.imread('KKB.jpeg', cv2.IMREAD_COLOR)
image_gray = cv2.imread('KKB.jpeg', cv2.IMREAD_GRAYSCALE)
cv2.imshow('BGR', image_BGR)
cv2.imshow('gray', image_gray)
cv2.waitKey()
cv2.destroyAllWindows()

输出效果如下:

  1. 图像保存

使用OpenCV显示图片文件,可以使用函数cv2.imwrite(file, img, num),例如:

cv2.imwrite('testimage.jpeg', image_BGR)
# cv2.imwrite('testimage.jpeg', image_BGR, [int(cv2.IMWRITE_JPEG_QUALITY), 95])
# cv2.imwrite('testimage.jpeg', image_BGR, [int(cv2.IMWRITE_PNG_COMPRESSION), 9])

这个API有三个参数:第一个参数是要保存的文件路径,第二个参数是要保存的图像。第三个参数是可选参数,它针对特定的格式:对于JPEG,其表示的是图像的质量,用0 - 100的整数表示,默认95;对于png ,第三个参数表示的是压缩级别,默认为3。

2 图像处理基础

2.1 像素处理

  1. 访问像素

在OpenCV中,我们可以直接以索引的方式访问图像的像素。例如我们访问刚才读取的图片(200, 200)坐标位置(左上角为坐标系原点)的像素可是使用:

import cv2
image_BGR = cv2.imread('KKB.jpeg', cv2.IMREAD_COLOR)
print(image_BGR[200,200])
>>> [246 218 177]

可见,在(200, 200)坐标位置所对应的三通道像素值分别为B:246,G:218,R:177。

  1. 修改像素

图像像素值的修改也十分简单,下面我们将原始图片中的一部分区域修改为红色(0, 0, 255):

import cv2
image_BGR = cv2.imread('KKB.jpeg', cv2.IMREAD_COLOR)
image_BGR[100:200, 100:200] = [0,0,255]
cv2.imshow('BGR', image_BGR)
cv2.waitKey()
cv2.destroyAllWindows()

所得到的结果为:

2.2 图像属性

  1. 图像形状

图像的形状可以通过image.shape获得,例如:

import cv2
image_BGR = cv2.imread('KKB.jpeg', cv2.IMREAD_COLOR)
print(image_BGR.shape)
>>> (684, 1067, 3)

可以看到,刚才我们打开的那张图片的高是684像素,宽是1067像素,通道数为3。

  1. 像素数目

图像的像素数目可以理解为图像中的像素值总量,也就是行*列*通道,可以通过image.size获得,例如:

import cv2
image_BGR = cv2.imread('KKB.jpeg', cv2.IMREAD_COLOR)
print(image_BGR.size)
>>> 2189484

我们来验证一下,刚才我们打开的那张图片的高是684像素,宽是1067像素,通道数为3,那他的像素数量应为这三者的乘积,即为 684 ∗ 1067 ∗ 3 = 2189484 684*1067*3=2189484 68410673=2189484,与上述代码中计算所得相同。

  1. 图像类型

图像的类型可以通过image.dtype获得,例如:

import cv2
image_BGR = cv2.imread('KKB.jpeg', cv2.IMREAD_COLOR)
print(image_BGR.dtype)
>>> uint8

由此可见,这张图片的属性是uint8。

3 图像运算

3.1 图像加法

我们知道,以uint8形式存储的图片的取值范围是[0, 255],即0代表纯黑,1代表纯白,0~1之间的值则表示由深到浅的灰色。那么在对图像做加法的时候,就会产生一个问题:像素值为100的图片+像素值为100的图片,可以获得像素值为200的图片,但如果是150+150,两张图片相加之后的像素值超出255的范围怎么办?在这时候,有两种解决方案。

  1. 取模运算

一般来说我们可以直接使用+进行取模运算,即image_c = image_a + image_b。取模运算顾名思义,就是对运算结果取模,此时两个像素值的相加大家可以理解为:

def image_add(pixel_a, pixel_b):
  	if pixel_a + pixel_b <= 255:
      	return pixel_a + pixel_b
    if pixel_a + pixel_b > 255:
      	return (pixel_a + pixel_b) % 255

也就是在不超出255范围时: 100 + 100 = 200 100+100=200 100+100=200,在超出255范围时: 150 + 150 = ( 150 + 150 ) % 255 = 45 150+150=(150+150)%255=45 150+150=(150+150)%255=45

  1. 饱和运算

饱和运算就更好理解了,两个像素值相加,如果超出255的限制,则直接取255。使用cv2.add(a, b)即可进行饱和运算。

取模运算和饱和运算的代码及效果图如下:

import cv2
image_a = cv2.imread('dog.jpeg', cv2.IMREAD_GRAYSCALE)
image_b= cv2.imread('cat.jpeg', cv2.IMREAD_GRAYSCALE)

image_c = image_a + image_b
image_d = cv2.add(image_a, image_b)

cv2.imshow('image_a', image_a)
cv2.imshow('image_b', image_b)
cv2.imshow('image_c', image_c)
cv2.imshow('image_d', image_d)
cv2.waitKey()
cv2.destroyAllWindows()

3.2 图像融合

图像融合其实也是图像加法的一种, 图像融合为两张图像赋予了不同的权重,从而使图像具有混合或透明的感觉。在OpenCV中,可以使用cv2.addWeighted(src1, alpha, src2, beta, gamma[, dst[, dtype]])来进行图像融合,此函数会依据下列表达式来进行运算 d s t = s r c 1 ∗ a l p h a + s r c 2 ∗ b e t a + g a m m a dst = src1 * alpha + src2 * beta + gamma dst=src1alpha+src2beta+gamma,也就是对图片1和图片2分别乘一个系数后相加,并添加gamma作为偏置。图像融合的代码及效果图如下:

import cv2
image_a = cv2.imread('dog.jpeg', cv2.IMREAD_GRAYSCALE)
image_b= cv2.imread('cat.jpeg', cv2.IMREAD_GRAYSCALE)

image_c = cv2.addWeighted(image_a, 0.5, image_b, 0.5, 0)

cv2.imshow('image_a', image_a)
cv2.imshow('image_b', image_b)
cv2.imshow('image_c', image_c)
cv2.waitKey()
cv2.destroyAllWindows()

4 图像几何变换

4.1 图像缩放

图像缩放其实就是改变图像的大小、形状,可以用下列API来实现:

Image = cv2.resize(src, dsize[, dst[, fx[, fy[, interpolation]]]])

这个API的参数较多,但其实很好理解,下面就是API的参数解释:

  • Image:输出图像
  • src:输入图像
  • dsize:输出图像的尺寸
  • fx:横坐标缩放比例
  • fy:纵坐标缩放比例
  • interpolation:缩放方式

在这些参数中,输入、输出图像都很好理解,输出图像的尺寸dsize是(宽,高),fxfy一般可直接使用0-1的缩放比例,值得注意的一点是,在给定dsize时,就不用另外输入缩放比例了,而想使用缩放比例时,disze应输入None(不可不输入)。缩放方式一般不填,直接使用默认值即可,其他缩放方式如下:

  • INTER_NEAREST 最近邻插值
  • INTER_LINEAR 双线性插值(默认设置)
  • INTER_AREA 使用像素区域关系进行重采样。 它可能是图像抽取的首选方法,因为它会产生无云纹理的结果。 但是当图像缩放时,它类似于INTER_NEAREST方法。
  • INTER_CUBIC 4x4像素邻域的双三次插值
  • INTER_LANCZOS4 8x8像素邻域的Lanczos插值

图像缩放的代码如下:

import cv2
image = cv2.imread('dog.jpeg', cv2.IMREAD_GRAYSCALE)
print(image.shape)
>>> (224, 225)
image = cv2.resize(image,(175,175))
print(image.shape)
>>> (175, 175)

4.2 图像翻转

图像的翻转可以使用cv2.flip(src, flipCode)实现,在这个API中需要输入一个翻转的模式flipCode:

  • flipCode为0代表垂直翻转(沿X轴翻转);
  • flipCode大于0代表水平翻转(沿Y轴翻转);
  • flipCode小于0代表水平垂直翻转(先沿X轴翻转,再沿Y轴翻转,等价于旋转180°)

图片翻转的代码及样例图如下:

import cv2
image= cv2.imread('cat.jpeg', cv2.IMREAD_GRAYSCALE)
image = cv2.resize(image,(300,300))
image_a = cv2.flip(image, -1)
image_b = cv2.flip(image, 0)
image_c = cv2.flip(image, 1)

cv2.imshow('image', image)
cv2.imshow('image_a', image_a)
cv2.imshow('image_b', image_b)
cv2.imshow('image_c', image_c)
cv2.waitKey()
cv2.destroyAllWindows()

4.3 图像旋转

图像的旋转比翻转要复杂一些,图像旋转过程中,要先求得旋转矩阵,而后在通过仿射变化函数对图像进行旋转。

cv2.getRotationMatrix2D(center, angle, scale) # 旋转矩阵
cv2.warpAffine(src, M, dsize[, dst[, flags[, borderMode[, borderValue]]]]) → dst # 仿射变化

参数说明

getRotationMatrix2D:

  • center–表示旋转的中心点
  • angle–表示旋转的角度degrees
  • scale–图像缩放因子

warpAffine:

  • src – 输入的图像
  • M – 2 X 3 的变换矩阵.
  • dsize – 输出的图像的size大小
  • dst – 输出的图像
  • flags – 输出图像的插值方法
  • borderMode – 图像边界的处理方式
  • borderValue – 当图像边界处理方式为BORDER_CONSTANT 时的填充值

图片旋转的代码及样例图如下(顺时针转90度):

import cv2
image = cv2.imread('dog.jpeg', cv2.IMREAD_GRAYSCALE)
h, w = image.shape

M = cv2.getRotationMatrix2D((w//2,h//2),-90,1.0)
dst = cv2.warpAffine(image,M,(w,h))

cv2.imshow('dst', dst)
cv2.waitKey()
cv2.destroyAllWindows()

image

5 图像平滑处理

5.1 均值滤波

均值滤波是最简单的滤波器,它取卷积核区域下所有像素的平均值并替换中心元素,均值滤波的代码及样例图如下:

import cv2
image = cv2.imread('dog.jpeg')
img_mean = cv2.blur(image, (5,5)) # 原图,核心大小
cv2.imshow('image', image)
cv2.imshow('img_mean', img_mean)
cv2.waitKey()
cv2.destroyAllWindows()

5.2 中值滤波

中值滤波器是一种非线性滤波器,它的基本原理是:选择待处理像素的一个邻域中各像素值的中值来代替待处理的像素。它能使某像素的灰度值与周围领域内的像素比较接近,从而消除一些孤立的噪声点,所以中值滤波器能够很好的消除椒盐噪声。中值滤波的代码及样例图如下:

import cv2
image = cv2.imread('dog.jpeg')
img_median = cv2.medianBlur(image, 5) # 原图,核心大小
cv2.imshow('image', image)
cv2.imshow('img_median', img_median)
cv2.waitKey()
cv2.destroyAllWindows()

5.3 高斯滤波

高斯滤波也是一种常见的滤波器,与中值滤波不同的是,它是使用高斯核心来计算的:
h ( x , y ) = e − ( x 2 + y 2 ) 2 σ 2 h(x,y)=e^{frac{-(x^2+y^2)}{2sigma^2}} h(x,y)=e2σ2(x2+y2)
其中 ( x , y ) (x,y) (x,y)是图像中的点的坐标, σ sigma σ为标准差。x和y都是代表以核中心点为坐标原点的坐标值,对于而言 σ sigma σ,当 σ sigma σ比较小的时候,生成的高斯模板中心的系数比较大,而周围的系数比较小,这样对图像的平滑效果不明显。当比较大时 σ sigma σ,生成的模板的各个系数相差就不是很大,比较类似于均值模板,对图像的平滑效果比较明显。高斯滤波的代码及样例图如下:

import cv2
image = cv2.imread('dog.jpeg')
img_Guassian = cv2.GaussianBlur(image,(5,5),0) # 原图,核心大小,sigma
cv2.imshow('image', image)
cv2.imshow('img_Guassian', img_Guassian)
cv2.waitKey()
cv2.destroyAllWindows()

5.4 双边滤波

双边滤波是一种非线性滤波方法,是结合了图像的邻近度和像素值相似度的一种折中,在滤除噪声的同时可以保留原图的边缘信息。整个双边滤波是由两个函数构成:一个函数是由空间距离决定的滤波器系数,另外一个诗由像素差值决定的滤波器系数,双边滤波具体计算过程在这里就不赘述了。双边滤波的代码及样例图如下:

import cv2
image = cv2.imread('dog.jpeg')
img_bilater = cv2.bilateralFilter(image,9,75,75)
cv2.imshow('image', image)
cv2.imshow('img_bilater', img_bilater)
cv2.waitKey()
cv2.destroyAllWindows()

最后

以上就是冷酷自行车为你收集整理的OpenCV常用操作1 OpenCV入门基础2 图像处理基础3 图像运算4 图像几何变换5 图像平滑处理的全部内容,希望文章能够帮你解决OpenCV常用操作1 OpenCV入门基础2 图像处理基础3 图像运算4 图像几何变换5 图像平滑处理所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(51)

评论列表共有 0 条评论

立即
投稿
返回
顶部