opencv c++ (1):创建Mat对象的常用方法

1. 前言

对于学过的东西,想系统记录一下,这里记录的是在Ai 旅途中常用到的opencv 相关知识,快速带你进阶opencv

2. Mat类

opencv c++ 中最常见的就是Mat类型。Mat 它是一个类,它所创建的对象类似于python 版opencv 中numpy 数据结构,因此也可以把他理解为一个存放矩阵的容器。Mat类的详细介绍可以看官网的API,OpenCV: cv::Mat Class Reference

3. 创建Mat

如何创建Mat 对象,关键要知道它有哪些构造函数,下面介绍常用的一些构造函数。

3.1 Mat () 

Mat()是默认构造函数 。如下隐式创建一个Mat型的m,它不包含任何数据。

#include <iostream>
#include<opencv.hpp>
using namespace std;
using namespace cv;

int main()
{

	Mat m;  // 隐式调用, 显示调用为: Mat m = Mat(); 

	return 0;
}

3.2 Mat (int rows, int cols, int type)

Mat m(4, 4, CV_8UC3);

rows是矩阵的行,可以理解为图片的高;cols是矩阵的列,可以理解为图片的宽;type是mat的类型,形式为CV_深度_通道数。具体参看第4章节。

如下创建4*4的3通道的蓝色的一个图

#include "opencv01.h"
#include <iostream>
#include<opencv.hpp>
using namespace std;
using namespace cv;
int main()
{
    Mat m(4, 4, CV_8UC3);
    namedWindow("m", WINDOW_NORMAL);
    m = Scalar(255, 0, 0); //BGR
    cout << endl << m << endl;
    imshow("m", m);
    waitKey(0);

    return 0;
}

3.3 Mat(int rows, int cols, int type, const Scalar& s)

Mat m(4, 4, CV_8UC3, Scalar(255, 0, 0));

与3.2一个意思。

3.4 Mat(Size size, int type, const Scalar& s)

Mat m(Size(4, 4), CV_8UC3, Scalar(255, 0, 0));

扫描二维码关注公众号,回复: 17335413 查看本文章

与3.2一个意思。

3.5 Mat(int n, const int* size, int type, const Scalar& s)

创建一个全0的3维数组
 int ar[] = {3,2,4};
 Mat m(3, ar, CV_8UC1, Scalar::all(0));

3.6 其他方法

//复制构造函数

Mat m = src; //等价于Mat m(src)

Mat m(src);

Mat m = imread(string path); //读图

//复制构造函数 + 静态方法

Mat m1 = Mat::zeros(Size(4, 5), CV_8UC3); //全0
Mat m2 = Mat::ones(Size(4, 5), CV_8UC3);  //全1
Mat m3 = Mat::eye(Size(4, 5), CV_8UC3);   //单位矩阵 

//creat方法

Mat m;

m.create(int _rows, int _cols, int _type);

m.create(Size _sz, int _type);

...

3.7 Mat 的常用属性方法

...

    Mat m(cv::Size(4,5), CV_8UC3, Scalar(0,255,0));
   
    cout << endl << m << endl;

    //属性
    cout << "维度:" << m.dims << endl;
    cout << "行:" << m.rows << endl;
    cout << "列:" << m.cols << endl;
    cout << "形状:" << m.size << endl; //宽、高
    cout << "宽:" << m.size[0] << "\t" << "高:" << m.size[1] << endl;

    //方法
    cout << "通道数:" << m.channels() << endl;
    cout << "深度:" << m.depth() << endl;
    
...

结果:

[  0, 255,   0,   0, 255,   0,   0, 255,   0,   0, 255,   0;
   0, 255,   0,   0, 255,   0,   0, 255,   0,   0, 255,   0;
   0, 255,   0,   0, 255,   0,   0, 255,   0,   0, 255,   0;
   0, 255,   0,   0, 255,   0,   0, 255,   0,   0, 255,   0;
   0, 255,   0,   0, 255,   0,   0, 255,   0,   0, 255,   0]
维度:2
行:5
列:4
形状:5 x 4
宽:5   高:4
通道数:3
深度:0

4. Mat的数据类型type参数

以下表二是opencv 中定义的所有类型,其形式是CV_深度_通道数,如CV_8UC3,代表深度为8位无符号3通道数据类型。

mat 中有个depth()的成员函数,其返回值就是深度,如下表一:

对于图像来说基本上只会用到CV_8UC(n),其他看看了解一下就可以了。一般图像,记住一下几个就可以了。

C1 :单通道,灰色

C3 :三通道,BGR

C4 :四通道,BGRA, A代表透明度

像素深度 = 8 * 通道数。因为我们正常显示的图片都是CV_8U。imshow函数在显示图像时,会将各种类型的数据都映射到[0, 255]。

我们看一下代码:

#include<opencv.hpp>
using namespace std;
using namespace cv;

int main()
{
    Mat m1(512, 512, CV_8UC3, Scalar(0, 255, 0));
    Mat m2(512, 512, CV_16UC3, Scalar(0, 255, 0));
    imshow("m1", m1);
    imshow("m2", m2);
    imwrite("m1.jpg", m1);
    imwrite("m2.jpg", m2);
    waitKey(0);
    return 0;
}

结果:由于m2是CV_16UC3类型,其值[0, 65535]映射到[0, 255]就看起来是黑色的,

然后我们看一下保存的m1.jpg和m2.jpg,如下,我们可以看到图片都是绿色的,而且位深度都是8*3 = 24, 这说明,我们的jpg图片数据只能是8U格式。因此我们在用opencv做图像处理的时候一般定义mat为8U的格式。

表一:

返回值 深度 含义 取值范围
0 CV_8U 8位无符号整数 0~255
1 CV_8S 8位有符号整数 -128~127
2 CV_16U 16位无符号整数 0~65535
3 CV_16S 16位有符号整数 -32768~35767
4 CV_32S 32位有符号整数 -2147483648~-2147483647
6 CV_32F 32位单精度浮点数 -FLA_MAX~FLA_MAX
7 CV_64F 64位双精度浮点数 -DBL_MAX~DBL_MAX

表二:

#define  CV_8UC1   CV_MAKETYPE(CV_8U,1)
#define  CV_8UC2   CV_MAKETYPE(CV_8U,2)
#define  CV_8UC3   CV_MAKETYPE(CV_8U,3)
#define  CV_8UC4   CV_MAKETYPE(CV_8U,4)
#define  CV_8UC(n)   CV_MAKETYPE(CV_8U,(n))
#define  CV_8SC1   CV_MAKETYPE(CV_8S,1)
#define  CV_8SC2   CV_MAKETYPE(CV_8S,2)
#define  CV_8SC3   CV_MAKETYPE(CV_8S,3)
#define  CV_8SC4   CV_MAKETYPE(CV_8S,4)
#define  CV_8SC(n)   CV_MAKETYPE(CV_8S,(n))
#define  CV_16UC1   CV_MAKETYPE(CV_16U,1)
#define  CV_16UC2   CV_MAKETYPE(CV_16U,2)
#define  CV_16UC3   CV_MAKETYPE(CV_16U,3)
#define  CV_16UC4   CV_MAKETYPE(CV_16U,4)
#define  CV_16UC(n)   CV_MAKETYPE(CV_16U,(n))
#define  CV_16SC1   CV_MAKETYPE(CV_16S,1)
#define  CV_16SC2   CV_MAKETYPE(CV_16S,2)
#define  CV_16SC3   CV_MAKETYPE(CV_16S,3)
#define  CV_16SC4   CV_MAKETYPE(CV_16S,4)
#define  CV_16SC(n)   CV_MAKETYPE(CV_16S,(n))
#define  CV_32SC1   CV_MAKETYPE(CV_32S,1)
#define  CV_32SC2   CV_MAKETYPE(CV_32S,2)
#define  CV_32SC3   CV_MAKETYPE(CV_32S,3)
#define  CV_32SC4   CV_MAKETYPE(CV_32S,4)
#define  CV_32SC(n)   CV_MAKETYPE(CV_32S,(n))
#define  CV_32FC1   CV_MAKETYPE(CV_32F,1)
#define  CV_32FC2   CV_MAKETYPE(CV_32F,2)
#define  CV_32FC3   CV_MAKETYPE(CV_32F,3)
#define  CV_32FC4   CV_MAKETYPE(CV_32F,4)
#define  CV_32FC(n)   CV_MAKETYPE(CV_32F,(n))
#define  CV_64FC1   CV_MAKETYPE(CV_64F,1)
#define  CV_64FC2   CV_MAKETYPE(CV_64F,2)
#define  CV_64FC3   CV_MAKETYPE(CV_64F,3)
#define  CV_64FC4   CV_MAKETYPE(CV_64F,4)
#define  CV_64FC(n)   CV_MAKETYPE(CV_64F,(n))
#define  CV_16FC1   CV_MAKETYPE(CV_16F,1)
#define  CV_16FC2   CV_MAKETYPE(CV_16F,2)
#define  CV_16FC3   CV_MAKETYPE(CV_16F,3)
#define  CV_16FC4   CV_MAKETYPE(CV_16F,4)
#define  CV_16FC(n)   CV_MAKETYPE(CV_16F,(n))

猜你喜欢

转载自blog.csdn.net/m0_59156726/article/details/129975736