【OpenCv】 Mat的一些简单使用技巧

机器学习的相关算法的实现需要大量使用到矩阵运算。用C++实现的话,OpenCv里面的Mat数据结构是一个很好的选择。

初始化

  • 创建cv::Mat,并且初始化cv::Scalar::all(0)
  • cv::Mat 可以直接使用cout进行输出
cv::Mat a(3, 3, CV_32FC1, cv::Scalar::all(0));
cout << a << endl;

使用数组初始化

int bArray[3][3] = { {1, 2, 3}, {4, 5, 6}, {7, 8, 9} };
cv::Mat b(3, 3, CV_8UC1, bArray);

PS: CV_8UC1代表的含义(摘抄自这里

CV_<bit_depth>(S|U|F)C<number_of_channels>

 1--bit_depth---比特数---代表8bite,16bites,32bites,64bites---举个例子吧--比如说,如
    如果你现在创建了一个存储--灰度图片的Mat对象,这个图像的大小为宽100,高100,那么,现在这张
    灰度图片中有10000个像素点,它每一个像素点在内存空间所占的空间大小是8bite,8位--所以它对
    应的就是CV_8
 2--S|U|F--S--代表---signed int---有符号整形
           U--代表--unsigned int--无符号整形
           F--代表--float---------单精度浮点型
 3--C<number_of_channels>----代表---一张图片的通道数,比如:
     1--灰度图片--grayImg---是--单通道图像
     2--RGB彩色图像---------是--3通道图像
     3--带Alph通道的RGB图像--是--4通道图像

.create()函数
可以创建规定大小的Mat
然后使用.at<_type>(i, j)赋值

	cv::Mat c;
	c.create(3, 3, CV_32FC1);
	c.at<float>(0, 0) = 1;
	c.at<float>(0, 1) = 2;
	c.at<float>(0, 2) = 3;

	c.at<float>(1, 0) = 4;
	c.at<float>(1, 1) = 5;
	c.at<float>(1, 2) = 6;

	c.at<float>(2, 0) = 7;
	c.at<float>(2, 1) = 8;
	c.at<float>(2, 2) = 9;
	cout << "c" << endl << c << endl;

下面是.at<type>的对应表
Mat
---------CV_8U

Mat-----------CV_8S

Nat_---------CV_16S

Mat_--------CV_16U

Mat_-----------CV_32S

Mat_----------CV_32F

Mat_--------CV_64F

cv::Scalar = cv::sum(cv::Mat scr)
求和函数
src中所有的值求和

	cv::Scalar sc = cv::sum(c);
	cout << sc[0] << endl;   //输出和!!!

如果按照某个维度来求和,就需要使用**reduce()**函数

	//1 表示按行求和
	//0 表示按列求和
	cv::reduce(c, cc, 1, CV_REDUCE_SUM);
	cout << "cc" << endl << cc << endl;

在这里插入图片描述

	cout << c.dims << endl;   //输出维度
	cout << c.rows << endl;   //输出行数
	cout << c.cols << endl;   //输出列数

深浅复制问题
直接用 = 赋值的话,就是传引用而已
.clone() 是拷贝一份新的

	cv::Mat copyC = c;
	copyC.at<float>(0, 0) = 10;
	cout << "c:" << endl << c << endl;  //c也被更改了
	cout << "copyC:" << endl << copyC << endl;
	c.at<float>(0, 0) = 1;
	cv::Mat copyC1 = c.clone();
	copyC1.at<float>(0, 0) = 10;
	cout << "c:" << endl << c << endl;  //c未被更改了
	cout << "copyC1:" << endl << copyC1 << endl;

.copyTo(dst)

	for (int i = 0; i < c.cols; i++)
	{
		cc.copyTo(c.col(i));  //把cc(列向量)复制到c的第i列上面
	}
	cout << c << endl;
cc = cc.t();  //矩阵转置
	for (int i = 0; i < c.rows; i++)
	{
		cc.copyTo(c.row(i));   //cc是列向量,不可以为行向量赋值。但是加上cc = cc.t(); 之后就可以了
	}
	cout << c << endl;

所有的调试代码;
以后学习到了在加

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

int main()
{
	cv::Mat a(3, 3, CV_32FC1, cv::Scalar::all(0));
	cout << "a" << endl;
	cout << a << endl;

	int bArray[3][3] = { {1, 2, 3}, {4, 5, 6}, {7, 8, 9} };
	cv::Mat b(3, 3, CV_8UC1, bArray);
	cout << "b" << endl;
	cout << b << endl;

	cv::Mat c;
	c.create(3, 3, CV_32FC1);
	c.at<float>(0, 0) = 1;
	c.at<float>(0, 1) = 2;
	c.at<float>(0, 2) = 3;

	c.at<float>(1, 0) = 4;
	c.at<float>(1, 1) = 5;
	c.at<float>(1, 2) = 6;

	c.at<float>(2, 0) = 7;
	c.at<float>(2, 1) = 8;
	c.at<float>(2, 2) = 9;
	cout << "c" << endl << c << endl;

	//cv::Mat cc;
	cv::Scalar sc = cv::sum(c);
	cout << "sum C = " << sc[0] << endl;

	//reduce()
	cv::Mat cc;
	//1 表示按行求和
	//0 表示按列求和

	cv::reduce(c, cc, 1, CV_REDUCE_SUM);
	cout << "cc" << endl << cc << endl;


	cout << c.dims << endl;   //输出维度
	cout << c.rows << endl;   //输出行数
	cout << c.cols << endl;   //输出列数

	//复制
	cv::Mat copyC = c;
	copyC.at<float>(0, 0) = 10;
	cout << "c:" << endl << c << endl;  //c也被更改了
	cout << "copyC:" << endl << copyC << endl;

	c.at<float>(0, 0) = 1;
	cv::Mat copyC1 = c.clone();
	copyC1.at<float>(0, 0) = 10;
	cout << "c:" << endl << c << endl;  //c未被更改了
	cout << "copyC1:" << endl << copyC1 << endl;

	


	for (int i = 0; i < c.cols; i++)
	{
		cc.copyTo(c.col(i));  //把cc(列向量)复制到c的第i列上面
	}
	cout << c << endl;

	
	cc = cc.t();
	for (int i = 0; i < c.rows; i++)
	{
		cc.copyTo(c.row(i));   //cc是列向量,不可以为行向量赋值
	}
	cout << c << endl;

	//int tt;
	//cin >> tt;
}
  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值