视觉SLAM笔记(24) 图像基础操作
1. OpenCV
OpenCV提供了大量的开源图像算法,是计算机视觉中使用极广的图像处理算法库
在使用之前,建议从源代码安装它
在ubuntu 下,可以选择从源代码安装和只安装库文件两种方式:
- 从源代码安装,是指从 OpenCV 网站下载所有的 OpenCV 源代码
并在机器上编译安装,以便使用
好处是可以选择的版本比较丰富,而且能看到源代码,不过需要花费一些编译时间 - 只安装库文件,是指通过 Ubuntu 来安装由 Ubuntu 社区人员已经编译好的库文件,这样就无需重新编译一遍
由于使用较新版本的 OpenCV,所以必须从源代码来安装它
从 OpenCV官网 中下载,选择 sources 版本即可,或者在 GitHub 下载也行
会获得一个像 opencv-4.1.1.zip
这样的压缩包
将它解压到任意目录下,发现 OpenCV 亦是一个 cmake 工程
在编译之前,先来安装 OpenCV 的依赖项:
$ sudo apt-get install build-essential libgtk2.0-dev libvtk5-dev libjpeg-dev libtiff5-dev libjasper-dev
事实上 OpenCV 的依赖项很多,缺少某些编译项会影响它的部分功能(不过也不会用到所有功能)
OpenCV 会在 cmake 阶段检查依赖项是否会安装,并调整自己的功能
如果电脑上有 GPU 并且安装了相关依赖项, OpenCV 也会把 GPU 加速打开
随后的编译安装和普通的 cmake 工程一样
$ mkdir build
$ cd build
$ cmake ..
cmake 过程中可以会遇到下载ippicv缓慢的问题,可以参考 源码编译OpenCV卡在ippicv 博文解决问题
如果 CPU 比较强力,可以使用命令调用多个线程进行编译(-j 后边的参数就是使用的线程数量)
为了节约时间,建议还是调用多个线程进行编译
$ make -j4
也可以和平时一样
$ make
视机器配置,这个编译过程大概需要十分钟到一个小时不等
顺利完成
然后,将 OpenCV 安装到机器上(而不是仅仅编译它)
$ sudo make install
在安装之后, OpenCV默认存储到 /usr/local
目录下
2. 操作图像
创建imageBasics.cpp
文件
#include <iostream>
#include <chrono>
using namespace std;
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
int main ( int argc, char** argv )
{
// 默认构造函数,创建矩阵存储图像
cv::Mat image;
// 读取指定路径下的图像
image = cv::imread ( argv[1] );
// 判断图像文件是否正确读取
if ( image.data == nullptr ) //数据不存在,可能是文件不存在
{
cerr<<"文件"<<argv[1]<<"不存在."<<endl;
return 0;
}
// 文件顺利读取, 首先输出一些基本信息
cout<<"图像宽为"<<image.cols<<",高为"<<image.rows<<",通道数为"<<image.channels()<<endl;
cv::imshow ( "image", image ); // 用cv::imshow显示图像
// 暂停程序,等待一个按键输入
cv::waitKey ( 0 );
// 判断image的类型
if ( image.type() != CV_8UC1 && image.type() != CV_8UC3 )
{
// 图像类型不符合要求
cout<<"请输入一张彩色图或灰度图."<<endl;
return 0;
}
// 遍历图像, 请注意以下遍历方式亦可使用于随机像素访问
// 使用 std::chrono 来给算法计时
chrono::steady_clock::time_point t1 = chrono::steady_clock::now();
for ( size_t y=0; y<image.rows; y++ )
{
for ( size_t x=0; x<image.cols; x++ )
{
// 访问位于 x,y 处的像素
// 用cv::Mat::ptr获得图像的行指针
unsigned char* row_ptr = image.ptr<unsigned char> ( y ); // row_ptr是第y行的头指针
unsigned char* data_ptr = &row_ptr[ x*image.channels() ]; // data_ptr 指向待访问的像素数据
// 输出该像素的每个通道,如果是灰度图就只有一个通道
for ( int c = 0; c != image.channels(); c++ )
{
unsigned char data = data_ptr[c]; // data为I(x,y)第c个通道的值
}
}
}
chrono::steady_clock::time_point t2 = chrono::steady_clock::now();
chrono::duration<double> time_used = chrono::duration_cast<chrono::duration<double>>( t2-t1 );
cout<<"遍历图像用时:"<<time_used.count()<<" 秒。"<<endl;
cv::waitKey ( 0 );
// 关于 cv::Mat 的拷贝
// 直接赋值并不会拷贝数据
cv::Mat image_another = image;
// 修改 image_another 会导致 image 发生变化
image_another ( cv::Rect ( 0,0,100,100 ) ).setTo ( 0 ); // 将左上角100*100的块置零
cv::imshow ( "image", image );
cv::waitKey ( 0 );
// 使用clone函数来拷贝数据
cv::Mat image_clone = image.clone();
image_clone ( cv::Rect ( 0,0,100,100 ) ).setTo ( 128 );
cv::imshow ( "image", image );
cv::imshow ( "image_clone", image_clone );
cv::waitKey ( 0 );
// 对于图像还有很多基本的操作,如剪切,旋转,缩放等
// 限于篇幅就不一一介绍了,请参看OpenCV官方文档查询每个函数的调用方法
cv::destroyAllWindows();
return 0;
}
cv::Mat
:矩阵类,除了表示图像之外,也可以用它来存储位姿等矩阵数据
只是一般认为 Eigen 对于固定大小的矩阵,使用起来效率更高一些
以上包括了图像读取、显示、像素遍历、拷贝、赋值等
编译该程序时,需要在 CMakeLists.txt
添加 OpenCV 的头文件,然后把程序链接到库文件上
同时,由于使用了 C++ 11 标准(如 nullptr 和 chrono),还需要设置一下编译器
# 声明要求的 cmake 最低版本
cmake_minimum_required( VERSION 2.8 )
# 声明一个 cmake 工程
project( imageBasics )
# 添加c++ 11标准支持
set( CMAKE_CXX_FLAGS "-std=c++11" )
# 寻找OpenCV库
find_package( OpenCV REQUIRED )
# 添加头文件
include_directories( ${OpenCV_INCLUDE_DIRS} )
# 添加一个可执行程序
add_executable( imageBasics imageBasics.cpp )
# 链接OpenCV库
target_link_libraries( imageBasics ${OpenCV_LIBS} )
3. 操作效果
在文件中存放了一张vae的漫画图片,就以对这图片为例进行操作
执行命令
$ ./imageBasics ../vae.png
程序先读取vae.png
文件,然后输出一些基本信息并且显示图像
然后暂停程序,等待一个按键输入
这里要确保是在图片窗口输入按键,其他地方是无效的
随便一个按键输入
遍历图像,并且输出使用的时间15.4毫秒左右
这里使用的是 cmake 默认的 debug 模式,如果使用 release 模式会快很多
然后暂停程序,等待一个按键输入
随便一个按键输入
左上角100*100的块置零
然后暂停程序,等待一个按键输入
随便一个按键输入
拷贝数据,并修改数据并显示
参考:
相关推荐:
视觉SLAM笔记(23) 图像
视觉SLAM笔记(22) RGB-D相机模型
视觉SLAM笔记(21) 双目相机模型
视觉SLAM笔记(20) 单目相机模型
视觉SLAM笔记(19) 相似变换群与李代数
谢谢!
上一篇: 有关current的文章推荐10篇
推荐阅读
-
视觉SLAM笔记(53) g2o 操作后端优化
-
视觉SLAM笔记(54) Ceres 操作后端优化
-
深度学习02-(计算机视觉基础、图像色彩操作、图像形态操作理论)
-
高翔视觉slam14讲学习笔记(3-李群、李代数 Sophus库基础学习)
-
Web学习笔记之html基础操作_常用标签(一)_2020_03_24
-
Web学习笔记之html基础操作_常用标签(二)_2020_03_24
-
Web学习笔记之html基础操作_常用标签(4)_优化及补充_2020_03_24
-
深度学习02-(计算机视觉基础、图像色彩操作、图像形态操作理论)
-
计算机视觉之OpenCV图像的基础操作
-
视觉SLAM笔记(24) 图像基础操作