因项目需要,最近在研究C++如何读取matlab的.mat文件,本文主要内容包括读取矩阵储存的.mat文件和结构体储存的.mat文件。
话不多说,直接上代码:
#include <mat.h>
#include <iostream>
#include <opencv2/opencv.hpp>
using namespace std;
using namespace cv;
int main()
{
//**********************使用c++读mat文件****************************
MATFile *pmatFile = NULL;
mxArray *pMxArray = NULL;
double *initA;
pmatFile = matOpen("Bessel_zeros.mat", "r");
pMxArray = matGetVariable(pmatFile, "zz"); //读取变量为zz的二维矩阵
initA = (double*)mxGetData(pMxArray);
int M = mxGetM(pMxArray);
int N = mxGetN(pMxArray);
cout << M << " x " << N << endl;
matClose(pmatFile);
mxFree(initA);
//end
//********************读取结构体中的三通道图像**********************
//结构体名:icons
//成员:folder,file,print------三个三通道的小图标
MATFile *pmatFile2 = NULL;
mxArray *pMxArray2 = NULL;
mxArray *pMxArrayFolder = NULL;
pmatFile2 = matOpen("icons.mat", "r");
pMxArray2 = matGetVariable(pmatFile2, "icons");
pMxArrayFolder = mxGetField(pMxArray2, 0, "folder");
if (pMxArray2 == NULL)
{
cout << "Error reading existing matrix !!!" << endl;
return -1;
}
//size 存储图像的各维度参数
const size_t *size;
size = mxGetDimensions(pMxArrayFolder);
int m_height = *size;//高
int m_width = *(size + 1);//宽
int m_channels = *(size + 2);//通道数
int m_imgSize = m_height*m_width;
//mxGetPr获取mat数据指针
double *pMatl = (double*)mxGetPr(pMxArrayFolder);
cout << m_height << " x " << m_width << " x " << m_channels << endl;
Mat Im(m_height, m_width, CV_64FC3);
for (int x = 0; x < m_height; x++)
{
double *p = Im.ptr<double>(x);
for (int y = 0; y < m_width; y++)
{
for (int j = 0; j < m_channels; j++)
{
p[y * m_channels + j] = pMatl[j*m_imgSize + m_height*y + x] * 255;
}
}
}
//end
Mat dst;
Im.convertTo(dst, CV_8UC3);
imshow("dst:", dst);
waitKey(0);
return 0;
}
在matlab中矩阵在内存中的顺序是按列存储的,对于三维矩阵是:第一维按列存储,接着第二维按列储存,第三维按列储存。对于opencv中的mat结构,是row * (col * channels)的方式,即按行存储,其中每行的(row,col)坐标对应的内容三通道并排。
参考博客: