内容简介:Mat是opencv2.0版本开始替换原来指针的一个数据结构,以前opencv1.0时代储存图像的变量都是以指针的形式,这样存在着一个弊端,每次定义图像变量流程便是,以传统c语言的方式去申请内存,使用完毕之后要记得手动释放,假如忘记了就会造成内存泄漏。而opencv2.0版本以后开始全面支持c++,同时也把mat作为图像数据变量的容器,它本质上是一个类,最大的优点是不需要像指针那样每次使用完都要手动释放内存,其内存管理是自动的。不需要花费精力去担心内存的管理问题,其实现的原理大致和c++新标准的智能指针类
Mat
Mat是opencv2.0版本开始替换原来指针的一个数据结构,以前opencv1.0时代储存图像的变量都是以指针的形式,这样存在着一个弊端,每次定义图像变量流程便是,以传统 c语言 的方式去申请内存,使用完毕之后要记得手动释放,假如忘记了就会造成内存泄漏。而opencv2.0版本以后开始全面支持c++,同时也把mat作为图像数据变量的容器,它本质上是一个类,最大的优点是不需要像指针那样每次使用完都要手动释放内存,其内存管理是自动的。不需要花费精力去担心内存的管理问题,其实现的原理大致和c++新标准的智能指针类似,是采用一种引用计数的方式去记录mat变量的使用,mat变量被使用或者赋值到一个新的变量名(浅拷贝),计数器就会自动加一,变量名被销毁了计数器就自动减一,当计数器值减到0时就会自动调用析构函数释放内存。
查看文档了解一下mat类
先看看mat类的继承派生关系图
常见的构造函数
Mat () Mat (int rows, int cols, int type) Mat (Size size, int type) Mat (int rows, int cols, int type, const Scalar &s) Mat (Size size, int type, const Scalar &s) Mat (int ndims, const int *sizes, int type) Mat (const std::vector< int > &sizes, int type) Mat (int ndims, const int *sizes, int type, const Scalar &s) Mat (const std::vector< int > &sizes, int type, const Scalar &s) Mat (const Mat &m) Mat (int rows, int cols, int type, void *data, size_t step=AUTO_STEP) Mat (Size size, int type, void *data, size_t step=AUTO_STEP) Mat (int ndims, const int *sizes, int type, void *data, const size_t *steps=0) Mat (const std::vector< int > &sizes, int type, void *data, const size_t *steps=0) Mat (const Mat &m, const Range &rowRange, const Range &colRange=Range::all()) Mat (const Mat &m, const Rect &roi) Mat (const Mat &m, const Range *ranges) Mat (const Mat &m, const std::vector< Range > &ranges)
模板的构造函数
template<typename _Tp > Mat (const std::vector< _Tp > &vec, bool copyData=false) template<typename _Tp , int n> Mat (const Vec< _Tp, n > &vec, bool copyData=true) template<typename _Tp , int m, int n> Mat (const Matx< _Tp, m, n > &mtx, bool copyData=true) template<typename _Tp > Mat (const Point_< _Tp > &pt, bool copyData=true) template<typename _Tp > Mat (const Point3_< _Tp > &pt, bool copyData=true) template<typename _Tp > Mat (const MatCommaInitializer_< _Tp > &commaInitializer) Mat (const cuda::GpuMat &m)
下面直接贴上代码解释,源代码为opencv samples里面的mat_the_basic_image_container.cpp文件
/* For description look into the help() function. */
//头文件
#include "opencv2/core.hpp"
#include <iostream>
//命名空间,建议显示使用,如cv::imshow
using namespace std;
using namespace cv;
//帮助信息函数
static void help()
{
cout
<< "\n---------------------------------------------------------------------------" << endl
<< "This program shows how to create matrices(cv::Mat) in OpenCV and its serial"
<< " out capabilities" << endl
<< "That is, cv::Mat M(...); M.create and cout << M. " << endl
<< "Shows how output can be formatted to OpenCV, python, numpy, csv and C styles." << endl
<< "Usage:" << endl
<< "./mat_the_basic_image_container" << endl
<< "-----------------------------------------------------------------------------" << endl
<< endl;
}
int main(int,char**)
{
//输出帮助信息
help();
// create by using the constructor
//! [constructor]
Mat M(2,2, CV_8UC3, Scalar(0,0,255));//使用构造函数创建mat容器, 2x2大小、8位无符号3通道,初始化为红色(opencv默认bgr)
cout << "M = " << endl << " " << M << endl << endl;
//! [constructor]
// create by using the create function()
//! [create]
M.create(4,4, CV_8UC(2));//使用create函数创建mat容器,4x4大小、8位无符号2通道
cout << "M = "<< endl << " " << M << endl << endl;
//! [create]
// create multidimensional matrices
//! [init]
int sz[3] = {2,2,2};
Mat L(3,sz, CV_8UC(1), Scalar::all(0));//创建多维矩阵、3维、每一维度为一个数组,8位无符号1通道、灰度初始化为0,三维的矩阵无法打印显示
//! [init]
// Cannot print via operator <<
// Create using MATLAB style eye, ones or zero matrix
//创建像matlab风格那样的单位矩阵、数值都为1或0的矩阵
//! [matlab]
Mat E = Mat::eye(4, 4, CV_64F); //单位矩阵
cout << "E = " << endl << " " << E << endl << endl;
Mat O = Mat::ones(2, 2, CV_32F);//数值全为1矩阵
cout << "O = " << endl << " " << O << endl << endl;
Mat Z = Mat::zeros(3,3, CV_8UC1);//数值全为0矩阵
cout << "Z = " << endl << " " << Z << endl << endl;
//! [matlab]
// create a 3x3 double-precision identity matrix
//! [comma]
Mat C = (Mat_<double>(3,3) << 0, -1, 0, -1, 5, -1, 0, -1, 0);//逗号分隔符方式,用到<<运算符
cout << "C = " << endl << " " << C << endl << endl;
//! [comma]
// do the same with initializer_list
#ifdef CV_CXX11
//! [list]
C = (Mat_<double>({0, -1, 0, -1, 5, -1, 0, -1, 0})).reshape(3);//使用初始化列表的方式创建
cout << "C = " << endl << " " << C << endl << endl;
//! [list]
#endif
//! [clone]
Mat RowClone = C.row(1).clone();
cout << "RowClone = " << endl << " " << RowClone << endl << endl;//使用clone函数方式
//! [clone]
// Fill a matrix with random values
//! [random]
Mat R = Mat(3, 2, CV_8UC3);
randu(R, Scalar::all(0), Scalar::all(255));//创建包含随机数的矩阵
//! [random]
// Demonstrate the output formatting options
//! [out-default]
//格式化打印这些数据
cout << "R (default) = " << endl << R << endl << endl;//默认格式
//! [out-default]
//! [out-python]
cout << "R (python) = " << endl << format(R, Formatter::FMT_PYTHON) << endl << endl;//python风格
//! [out-python]
//! [out-numpy]
cout << "R (numpy) = " << endl << format(R, Formatter::FMT_NUMPY ) << endl << endl;//numpy风格
//! [out-numpy]
//! [out-csv]
cout << "R (csv) = " << endl << format(R, Formatter::FMT_CSV ) << endl << endl;//csv风格、即逗号分隔值风格
//! [out-csv]
//! [out-c]
cout << "R (c) = " << endl << format(R, Formatter::FMT_C ) << endl << endl;//c语言风格
//! [out-c]
//! [out-point2]
Point2f P(5, 1);//浮点型2维点
cout << "Point (2D) = " << P << endl << endl;
//! [out-point2]
//! [out-point3]
Point3f P3f(2, 6, 7);//浮点型3维点
cout << "Point (3D) = " << P3f << endl << endl;
//! [out-point3]
//! [out-vector]
vector<float> v;
v.push_back( (float)CV_PI); v.push_back(2); v.push_back(3.01f);
cout << "Vector of floats via Mat = " << Mat(v) << endl << endl;//向量转为mat类
//! [out-vector]
//! [out-vector-points]
vector<Point2f> vPoints(20);//浮点型2维点集合
for (size_t i = 0; i < vPoints.size(); ++i)
vPoints[i] = Point2f((float)(i * 5), (float)(i % 7));
cout << "A vector of 2D Points = " << vPoints << endl << endl;
//! [out-vector-points]
return 0;
}
代码知识点
1.使用构造函数创建mat容器
Mat M(2,2, CV_8UC3, Scalar(0,0,255));//使用构造函数创建mat容器, 2x2大小、8位无符号3通道,初始化为红色(opencv默认bgr) cout << "M = " << endl << " " << M << endl << endl;
2.使用create函数创建mat容器
M.create(4,4, CV_8UC(2));//使用create函数创建mat容器,4x4大小、8位无符号2通道 cout << "M = "<< endl << " " << M << endl << endl;
3.创建多维矩阵
int sz[3] = {2,2,2};
Mat L(3,sz, CV_8UC(1), Scalar::all(0));//创建多维矩阵、3维、每一维度为一个数组,8位无符号1通道、灰度初始化为0,三维的矩阵无法打印显示
4.创建像matlab风格那样的单位矩阵、数值都为1或0的矩阵
//! [matlab] Mat E = Mat::eye(4, 4, CV_64F); //单位矩阵 cout << "E = " << endl << " " << E << endl << endl; Mat O = Mat::ones(2, 2, CV_32F);//数值全为1矩阵 cout << "O = " << endl << " " << O << endl << endl; Mat Z = Mat::zeros(3,3, CV_8UC1);//数值全为0矩阵 cout << "Z = " << endl << " " << Z << endl << endl; //! [matlab]
5.其他方式创建矩阵
// create a 3x3 double-precision identity matrix
//! [comma]
Mat C = (Mat_<double>(3,3) << 0, -1, 0, -1, 5, -1, 0, -1, 0);//逗号分隔符方式,用到<<运算符
cout << "C = " << endl << " " << C << endl << endl;
//! [comma]
// do the same with initializer_list
#ifdef CV_CXX11
//! [list]
C = (Mat_<double>({0, -1, 0, -1, 5, -1, 0, -1, 0})).reshape(3);//使用初始化列表的方式创建
cout << "C = " << endl << " " << C << endl << endl;
//! [list]
#endif
//! [clone]
Mat RowClone = C.row(1).clone();
cout << "RowClone = " << endl << " " << RowClone << endl << endl;//使用clone函数方式
//! [clone]
// Fill a matrix with random values
//! [random]
Mat R = Mat(3, 2, CV_8UC3);
randu(R, Scalar::all(0), Scalar::all(255));//创建包含随机数的矩阵
//! [random]
6.格式化打印输出Mat类数据
cout << "R (default) = " << endl << R << endl << endl;//默认格式 //! [out-default] //! [out-python] cout << "R (python) = " << endl << format(R, Formatter::FMT_PYTHON) << endl << endl;//python风格 //! [out-python] //! [out-numpy] cout << "R (numpy) = " << endl << format(R, Formatter::FMT_NUMPY ) << endl << endl;//numpy风格 //! [out-numpy] //! [out-csv] cout << "R (csv) = " << endl << format(R, Formatter::FMT_CSV ) << endl << endl;//csv风格、即逗号分隔值风格 //! [out-csv] //! [out-c] cout << "R (c) = " << endl << format(R, Formatter::FMT_C ) << endl << endl;//c语言风格 //! [out-c]
输出的格式布置程序中的五种,查看文档可以看到Formatter有一个枚举变量,定义如下
enum {
FMT_DEFAULT = 0,
FMT_MATLAB = 1,
FMT_CSV = 2,
FMT_PYTHON = 3,
FMT_NUMPY = 4,
FMT_C = 5
}
7. 2D、3D和vector的使用方法
//! [out-point2]
Point2f P(5, 1);//浮点型2维点
cout << "Point (2D) = " << P << endl << endl;
//! [out-point2]
//! [out-point3]
Point3f P3f(2, 6, 7);//浮点型3维点
cout << "Point (3D) = " << P3f << endl << endl;
//! [out-point3]
//! [out-vector]
vector<float> v;
v.push_back( (float)CV_PI); v.push_back(2); v.push_back(3.01f);
cout << "Vector of floats via Mat = " << Mat(v) << endl << endl;//向量转为mat类
//! [out-vector]
//! [out-vector-points]
vector<Point2f> vPoints(20);//浮点型2维点集合
for (size_t i = 0; i < vPoints.size(); ++i)
vPoints[i] = Point2f((float)(i * 5), (float)(i % 7));
cout << "A vector of 2D Points = " << vPoints << endl << endl;
//! [out-vector-points]
8.运行截图
回顾总结
这个例程的知识点包含了mat类的实例化方法,包含构造函数、create函数、和克隆拷贝、初始化列表等,接着时特殊矩阵的创建,格式化输出mat类数据,最后时2D、3D和vector的使用方法。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网
猜你喜欢:- laravel自带用户认证
- Mac自带apache配置
- opencv自带例子学习-图像混合
- Golang中自带的强大命令工具
- Android调用系统自带的分享功能
- 使用oracle自带的命令进行导入导出
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
注意力经济: 如何把大众的注意力变成生意
吴修铭 / 中信出版集团股份有限公司 / 2018-4-1 / 69
编辑推荐 这本书由万维钢作序,并在《得到》日课中多次推荐!中文版未上市之前,中文前沿媒体就在力推这本书!关于注意力争夺战的历史和现在,作者给了权威的梳理和定位! 百年来,在争夺注意力的战场上,媒体、广告、商人、企业和大众成为博弈的主角。商人是如何在注意力争夺战中获利的?媒体是如何在改变报道形式的?广告是如何进化的?以及,营销是如何变得随处可见、无孔不入的呢?这本书讲述了令商人或企业从吸......一起来看看 《注意力经济: 如何把大众的注意力变成生意》 这本书的介绍吧!