学习OpenCV3: 第4章 图像和大型数组类型


1、稠密数组cv::Mat

cv::Mat构造函数 示例
默认构造函数 cv::Mat
构造二维数组 cv::Mat(int rows, int cols, int type)
cv::Mat(int rows, int cols, int type, const Scalar &s)
cv::Mat(int rows, int cols, int type, void *data, size_t step=AUTO_STEP)
cv::Mat(cv::Size sz, int type)
cv::Mat(cv::Size sz, int type, const Scalar &s)
cv::Mat(cv::Size sz, int type, void *data, size_t step=AUTO_STEP)
构造多维数组 cv::Mat(int ndims, const int *size, int type)
cv::Mat(int ndims, const int *size, int type, const Scalar &s)
cv::Mat(int ndims, const int *size, int type, void *data, size_t step=AUTO_STEP)
复制构造函数 cv::Mat(const cv::Mat &mat)
cv::Mat(const cv::MatExpr &expr)
cv::Mat(const cv::Mat &mat, const cv::Rect &roi)
cv::Mat(const cv::Mat &mat, const cv::Range &rows, const cv::Range &cols)
cv::Mat(const cv::Mat &mat, const cv::Range *ranges)
模板构造函数 cv::Mat(const cv::Vec<T,n> &vec, bool coptData=true)
cv::Mat(const cv::Matx<T,m,v> &matx, bool copyData=true)
cv::Mat(const std::vector<T> &vec, bool copyData=true)
静态方法 cv::Mat::zeros(int rows, int cols, int type)
cv::Mat::ones(int rows, int cols, int type)
cv::Mat::eye(int rows, int cols, int type)
  1. cv::Mat类可表示矩阵、图像和多维数组,可包含任何原始类型的组合,如数字、向量和其它类型。
  2. cv::Mat的类型:CV_{8U,16S,16U,32S,32F,64F}C{1,2,3}或者CV_{8U,16S,16U,32S,32F,64F}C({1,2,3,...})
  3. 对象cv::Mat是数据实体的头,其内部的数据指针类似于智能指针,指向数据实体。
Mat m;
m.create(3, 10, CV_32FC3); // 申请内存
m.setTo(Scalar(1.0f, 0.0f, 1.0f)); // 赋值
// 等价于
Mat m(3, 10, CV_32FC3, Scalar(1.0f, 0.0f, 1.0f));

2、访问元素和子区域

访问元素 实例
at<>() M.at<int>(i)
M.at<int>(pt)
M.at<float>(i, j)
M.at<float>(i, j, k)
M.at<uchar>(idx)
ptr<>() M.ptr<Vec3f>(i)
cvMatIterator_<>
cvMatConstIterator_<>
MatConstIterator_<Vec3f> it = m.begin<Vec3f>()
cv::NaryMatIterator const cv::Mat *arrays[] = {&n_mat, 0}
cv::Mat my_planes[1]
cv::NAryMatIterator it(arrays, my_planes)
it.planes[0]
区块访问 示例
row
col
m.row(i)
m.col(j)
rowRange
colRange
m.rowRange(i0, i1)
m.rowRange(cv::Range(i0, i1))
m.colRange(j0, j1)
m.colRange(cv::Range(j0, j1))
diag m.diag(d)
() m(cv::Range(i0, i1), cv::Range(j0, j1))
m(cv::Rect(i0, j0, w, h))
m(ranges)
  1. 访问元素的两种方法:通过位置或迭代器访问。位置访问包括at<>()ptr<>(),其中at<>()只读。迭代器访问包括cvMatIterator_<>cvMatConstIterator_<>cv::NaryMatIterator,其中cvMatConstIterator_<>只读。
  2. 数组按行组织,行内按顺序排列,行间因数据对齐可能有间隔。当使用ptr<>()遍历数组时需先通过isContinuous()确定数组行间数据是连续的。
  3. cvMatIterator_<>指向元素,cv::NaryMatIterator指向一个面(数组中连续内存的片段)。
  4. 区块访问会创建新的数组头,而不会复制数据,即等号左右两边的变量指向同一内存,修改左边的变量会相应改变右边的变量。

3、矩阵表达式

矩阵表达式支持的运算 示例
矩阵与矩阵的加减 m0 + m1, m0 - m1
矩阵与元素的加减乘 m0 + s, m0 - s, s + m0, s - m0
s * m0, m0 * s
矩阵元素的乘除 m0.mul(m1)
m0 / m1
矩阵乘法 m0 * m1
点乘和叉乘 m0.cross(m1), mo.dot(m1)
取绝对值 cv::abs(m0)
取最值 min(m0, m1), max(m0, m1)
min(m0, s), max(m0, s), min(s, m0), max(s, m0)
矩阵比较 m0 > m1, m0 >= m1, m0==m1, m0 < m1, m0 <= m1
逻辑操作 m0 & m1, m0 \| m1, m0 ^ m1, ~m0
m0 & s, s & m0, m0 \| s, s \| m0, m0 ^ s, s ^ m0
矩阵取负 -m0
逆矩阵 m0.inv(method)
转置矩阵 m0.t()
静态方法 cv::Mat::zeros(rows, cols, type)
cv::Mat::ones(rows, cols, type)
cv::Mat::eye(rows, cols, type)
  1. OpenCV在进行算术和其它操作时会自动检查是否上溢出和下溢出。cv::saturate_cast<>()可在溢出时将结果转换为相对最小或最大的可行值。

4、cv::Mat的其它函数成员

cv::Mat的其它函数成员 描述
m1 = m0.clone() 对m1重新分配内存并拷贝数据,m1与m0无关
m0.copyTo(m1)
m0.copyTo(m1, mask)
若m0与m1的size、type一致,则只拷贝数据
若不一致则重新分配内存并拷贝数据
mask存在,则只复制mask所指示的区域
m0.convertTo(m1, type, scale, offset) 转换m0中元素的类型(如CV_32F
尺度变换(默认为1)
增加偏置(默认为0)
m0.assignTo(m1, type) 只在内部使用,集成在convertTo
m0.setTo(s, mask) 设置m0所有元素为s
mask存在,则只对mask指示区域进行操作
m0.reshape(chan, rows) 改变二维数组的有效形状
chanrows为0,则不作修改
m0.push_back(s)
m0.push_back(m1)
在末尾增加m*1大小的数组
在m*n的m0末尾增加k行,m1大小必须是k*n
m0.pop_back(n) 从m*n的m0末尾移除n行,默认是1行,返回void类型
m0.locateROI(size, offset) offset是Point类型
获取offset处,大小为size的ROI。
m0.adjustROI(t, b, l, r) 通过t(above)、b(below)、l(left)、r(reft)调整ROI范围
m0.total() 计算数组元素的个数(不包括通道)
m0.isContinuous() 若m0行间无间隙,则返回true
m0.elemSize() 返回m0的位长度,如CV_32FC3,(32/8)*3=12
m0.elemSize1() 返回m0最基本元素的位长度,如CV_32FC3,32/8=4
m0.type() 返回m0元素的类型,如CV_32FC3
m0.depth() 返回m0通道中元素的类型,如CV_32F
m0.channels() 返回m0的通道数
m0.size() 返回m0的大小size
m0.size() 如m0无元素,则返回true,如m0.total==0或者m.data==NULL

5、稀疏数组cv::SparseMat

cv::SparseMat额外的类成员函数 示例
默认构造函数 cv::SparseMat sm
值构造函数 cv::SparseMat sm(3, sz, CV_32F)
复制构造函数 cv::SparseMat sm(sm0)
非0元素的数量 size_t n = sm.nzcount()
索引指向的数据的哈希值 size_t h = sm.hash(i0)
size_t h = sm.hash(i0, i1)
size_t h = sm.hash(i0, i1, i3)
size_t h = sm.hash(idx)
修改元素值 sm.ref<float>(i0) = f0
sm.ref<float>(i0, i1) = f0
sm.ref<float>(i0, i1, i2) = f0
sm.ref<float>(idx) = f0
获取元素值 f0 = sm.value<float>(i0)
f0 = sm.value<float>(i0, i1)
f0 = sm.value<float>(i0, i1, i2)
f0 = sm.value<float>(idx)
f0 = sm.find<float>(i0)
f0 = sm.find<float>(i0, i1)
f0 = sm.find<float>(i0, i1, i2)
f0 = sm.find<float>(idx)
移除元素 sm.erase(i0, i1, &hashval)
sm.erase(i0, i1, i2, &hashval)
sm.erase(idx, &hashval)
迭代器 cv::SparseMatIterator<float> it = sm.begin<float>()
cv::SparseMatIterator<uchar> it_end = sm.end<float>()
  1. cv::SparseMat在数组非0元素非常少时使用,如直方图,高维数组等。
  2. cv::Mat使用接近C风格的数组来存储数据,cv::SparseMat使用哈希表来存储非0元素。
  3. 直接访问稀疏数组元素的4种方法:cv::SparseMat::ptr()cv::SparseMat::ref()cv::SparseMat::value()cv::SparseMat::find()。其中cv::SparseMat::value()cv::SparseMat::find()只读。
  4. 迭代器访问稀疏数组的方法:cv::SparseMatIterator_<>cv::SparseMatConstIterator_<>cv::SparseMatIteratorcv::SparseMatConstIterator。其中cv::SparseMatConstIterator_<>cv::SparseMatConstIterator只读。node()返回一个指针,指向的稀疏矩阵的实际数据区域。
  5. cv::Mat_<>cv::SparseMat_<>是模板,其作用是在使用其成员函数是不用在调用其模板形式。

猜你喜欢

转载自blog.csdn.net/qq_34801642/article/details/107315593
今日推荐