|
|
# 6.2.1 OpenCV入门
|
|
|
|
|
|
## 什么是OpenCV
|
|
|
|
|
|
`OpenCV`是计算机视觉领域应用最广泛的开源工具包,基于`C/C++`,支持`Linux/Windows/MacOS/Android/iOS`,并提供了`Python,Matlab`和`Java`等语言的接口,因为其丰富的接口,优秀的性能和商业友好的使用许可,不管是学术界还是业界中都非常受欢迎。`OpenCV`最早源于`Intel`公司`1998`年的一个研究项目,当时在`Intel`从事计算机视觉的工程师盖瑞·布拉德斯基(`Gary Bradski`)访问一些大学和研究组时发现学生之间实现计算机视觉算法用的都是各自实验室里的内部代码或者库,这样新来实验室的学生就能基于前人写的基本函数快速上手进行研究。于是`OpenCV`旨在提供一个用于计算机视觉的科研和商业应用的高性能通用库。
|
|
|
|
|
|
第一个`alpha`版本的`OpenCV`于`2000`年的`CVPR`上发布,在接下来的5年里,又陆续发布了`5`个`beta`版本,`2006`年发布了第一个正式版。`2009`年随着盖瑞加入了`Willow Garage`,`OpenCV`从`Willow Garage`得到了积极的支持,并发布了`1.1`版。`2010`年`OpenCV`发布了`2.0`版本,添加了非常完备的`C++`接口,从`2.0`开始的版本非常用户非常庞大,至今仍在维护和更新。`2015`年`OpenCV 3`正式发布,除了架构的调整,还加入了更多算法,更多性能的优化和更加简洁的`API`,另外也加强了对`GPU`的支持,现在已经在许多研究机构和商业公司中应用开来。
|
|
|
|
|
|
## 安装OpenCV
|
|
|
|
|
|
想要安装`OpenCV`非常简单,只需在有网的环境下,在命令行中输入指令:`pip install opencv-python`即可安装。
|
|
|
|
|
|
安装好后,使用如下代码,若能成功运行,则说明安装成功。
|
|
|
|
|
|
```python
|
|
|
import cv2
|
|
|
print(cv2.__version__)
|
|
|
```
|
|
|
|
|
|
## 读取并显示图片
|
|
|
|
|
|
假设在当前目录有一张图片,图片名为`example.png`,那么可以使用`imread`函数读取图片,使用`namedWindow`函数创建显示图片的窗口,使用`imshow`函数显示图片。
|
|
|
|
|
|
```python
|
|
|
import cv2
|
|
|
# 读取图片
|
|
|
src=cv2.imread('./example.png')
|
|
|
# 创建一个标题为input_image的窗口
|
|
|
cv2.namedWindow('input_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 在标题为input_image的窗口上显示图片
|
|
|
cv2.imshow('input_image', src)
|
|
|
cv2.waitKey(0)
|
|
|
# 销毁窗口
|
|
|
cv2.destroyAllWindows()
|
|
|
```
|
|
|
|
|
|

|
|
|
|
|
|
## 图像缩放
|
|
|
|
|
|
有的时候,得到的原始图像数据集中的图像大小不一致,如果想要将图像缩放至固定的宽高,则可以使用`resize`函数实现功能。
|
|
|
|
|
|
```python
|
|
|
import cv2
|
|
|
# 读取图片
|
|
|
src=cv2.imread('./example.png')
|
|
|
# 将src图片缩放成宽为64个像素,高为64个像素的图像,并保存在dst变量中
|
|
|
dst = cv2.resize(src, (246, 256))
|
|
|
# 创建一个标题为input_image的窗口
|
|
|
cv2.namedWindow('input_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 创建一个标题为resized_image的窗口
|
|
|
cv2.namedWindow('resized_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 在标题为input_image的窗口上显示图片src
|
|
|
cv2.imshow('input_image', src)
|
|
|
# 在标题为resized_image的窗口上显示图片dst
|
|
|
cv2.imshow('resized_image', dst)
|
|
|
cv2.waitKey(0)
|
|
|
# 销毁窗口
|
|
|
cv2.destroyAllWindows()
|
|
|
```
|
|
|
|
|
|

|
|
|
|
|
|
## 彩色图转灰度图
|
|
|
|
|
|
有的时候颜色信息对于我们的任务来说并不是特别重要,此时可以使用`cvtColor`函数实现将彩色图转换成灰度图。
|
|
|
|
|
|
```python
|
|
|
import cv2
|
|
|
# 读取图片
|
|
|
src=cv2.imread('./example.png')
|
|
|
# 将图片src从BGR的彩色图转换成灰度图,并保存到dst
|
|
|
dst = cv2.cvtColor(src, cv2.COLOR_BGR2GRAY)
|
|
|
# 创建一个标题为input_image的窗口
|
|
|
cv2.namedWindow('input_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 创建一个标题为resized_image的窗口
|
|
|
cv2.namedWindow('gray_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 在标题为input_image的窗口上显示图片src
|
|
|
cv2.imshow('input_image', src)
|
|
|
# 在标题为resized_image的窗口上显示图片dst
|
|
|
cv2.imshow('gray_image', dst)
|
|
|
cv2.waitKey(0)
|
|
|
# 销毁窗口
|
|
|
cv2.destroyAllWindows()
|
|
|
```
|
|
|
|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
## 二值化
|
|
|
|
|
|
图像二值化就是将图像上的像素点的灰度值设置为`0`或`255`,也就是将整个图像呈现出明显的黑白效果的过程。二值化的原理就是找到一个合适的阈值`t`,然后遍历整张图片中所有的像素点,当像素点的灰度值高于阈值`t`时,将该像素点的灰度值置为`255`,否则置成`0`。`OpenCV`中提供了实现二值化的函数`threshold`。
|
|
|
|
|
|
```python
|
|
|
import cv2
|
|
|
# 读取图片,0表示读取到的图片为灰度图
|
|
|
src=cv2.imread('./example.png', 0)
|
|
|
# 对图片scr进行二值化,cv2.THRESH_OTSU表示自动找出合适的阈值,并将二值化后的图保存到dst
|
|
|
_, dst = cv2.threshold(src, 127, 255, cv2.THRESH_OTSU)
|
|
|
# 创建一个标题为input_image的窗口
|
|
|
cv2.namedWindow('input_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 创建一个标题为resized_image的窗口
|
|
|
cv2.namedWindow('gray_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 在标题为input_image的窗口上显示图片src
|
|
|
cv2.imshow('input_image', src)
|
|
|
# 在标题为resized_image的窗口上显示图片dst
|
|
|
cv2.imshow('gray_image', dst)
|
|
|
cv2.waitKey(0)
|
|
|
# 销毁窗口
|
|
|
cv2.destroyAllWindows()
|
|
|
```
|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
## 直方图均衡
|
|
|
|
|
|
对曝光过度或者逆光拍摄的图片可以通过直方图均衡化的方法用来增强局部或者整体的对比度。
|
|
|
|
|
|
具体思路是通过找出图像中最亮和最暗的像素值将之映射到纯黑和纯白之后再将其他的像素值按某种算法映射到纯黑和纯白之间的值。另一种方法是寻找图像中像素的平均值作为中间灰度值,然后扩展范围以达到尽量充满可显示的值。
|
|
|
|
|
|
|
|
|
什么是直方图?你可以把直方图看作一个图或图,它给你一个关于图像的强度分布的总体思路。它是一个带有像素值的图(从`0`到`255`,不总是)在`x`轴上,在`y`轴上的图像对应的像素个数。
|
|
|
|
|
|
这只是理解图像的另一种方式。通过观察图像的直方图,你可以直观地了解图像的对比度、亮度、亮度分布等。今天几乎所有的图像处理工具都提供了直方图上的特征。
|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
你可以看到图像和它的直方图。(这个直方图是用灰度图像绘制的,而不是彩色图像)。直方图的左边部分显示了图像中较暗像素的数量,右边区域显示了更明亮的像素。从直方图中可以看到,深色区域的像素数量比亮色区域更多,而中间色调的数量(中值大约在`127`左右)则少得多。
|
|
|
|
|
|
考虑一个图像,其像素值仅限制在特定的值范围内。例如,更明亮的图像将使所有像素都限制在高值中。但是一个好的图像会有来自图像的所有区域的像素。所以你需要把这个直方图拉伸到两端(如下图所给出的),这就是直方图均衡的作用(用简单的话说)。这通常会改善图像的对比度。
|
|
|
|
|
|

|
|
|
|
|
|
`OpenCV`中提供了实现直方图均衡的函数`equalizeHist`。
|
|
|
|
|
|
|
|
|
```python
|
|
|
import cv2
|
|
|
# 读取图片,0表示读取到的图片为灰度图
|
|
|
src=cv2.imread('./example.png', 0)
|
|
|
# 对图片scr进行直方图均衡,并将结果保存到dst
|
|
|
dst = cv2.equalizeHist(src)
|
|
|
# 创建一个标题为input_image的窗口
|
|
|
cv2.namedWindow('input_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 创建一个标题为resized_image的窗口
|
|
|
cv2.namedWindow('equalized_image', cv2.WINDOW_AUTOSIZE)
|
|
|
# 在标题为input_image的窗口上显示图片src
|
|
|
cv2.imshow('input_image', src)
|
|
|
# 在标题为resized_image的窗口上显示图片dst
|
|
|
cv2.imshow('equalized_image', dst)
|
|
|
cv2.waitKey(0)
|
|
|
# 销毁窗口
|
|
|
cv2.destroyAllWindows()
|
|
|
```
|
|
|
|
|
|

|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|