• opencv-cv::Mat


     如果使用Mat类,我们得到的好处是:

    不需要手动申请一块内存;
    在不需要时不用再手动释放内存;
    可以通过类的封装,方便的获取到数据的相关信息

    Mat类分为两个部分:矩阵头和矩阵数据。如果我们在操作一副图像的数据量时,矩阵数据的大小很大(一般约有1M的数据量),那么拷贝和赋值函数所作的操作如果的深拷贝的话,效率会大大的降低。所以,Opencv的做法是只复制其矩阵头信息,而矩阵数据采用引用的方式,即多个Mat对象共享同一个矩阵数据,这里使用的原理类似c++11中的共享指针

        cv::Mat A = cv::imread("D:/bb/tu/ma.jpg");
        cv::Mat B(A);
        cv::Mat C = A;
        printf("A.data = %p
    B.data = %p
    C.data = %p
    ", A.data, B.data, C.data);

    输出结果如下:

     如上我们可以看到,三个Mat类对象的矩阵数据的地址是一样的。那么释放内存的原则是怎样的呢。这个也是内部使用了引用计数的方法,类似共享指针,当引用计数变为0的时候才会真正的释放内存

    Mat对象的创建

        cv::Mat M1(5, 4, CV_8UC4, cv::Scalar(0, 0, 0, 255));//创建2维矩阵对象
        /*
        参数1和参数2:行数和列数
        参数3:图像属性8UC4:
              第一位8:比特数 代表8bite,16bites,32bites,64bites,每一个像素点在内存空间所占的空间大小
              第二位U:S--代表---signed int---有符号整形
                     U--代表--unsigned int--无符号整形
                     F--代表--float-------单精度浮点型
              最后两位c4:通道数:1--灰度图片---是--单通道图像
                              2--RGB彩色图像---------是--3通道图像
                              3--带Alph通道的RGB图像--是--4通道图像
        参数4:每个像素点的颜色
    */
    
        std::cout << M1 << std::endl; //显示数据
    
        int r=M1.rows;   //返回行数
        int c=M1.cols;   //返回列数
        
        qDebug()<<r<<c;
        cv::Mat M1(5, 4, CV_8UC3);
        std::cerr<<M1<<std::endl;
        M1=cv::Scalar(10, 20, 30);//赋值
        std::cerr<<M1<<std::endl;
        int sz[2]={5,4};
        cv::Mat M(2, sz, CV_8UC4, cv::Scalar(0, 0, 0, 255));//创建n维矩阵对象
        /*
        参数1:矩阵的维数
        参数2:是个数组,表示行数和列数
        */
    
        std::cout << M << std::endl; 
        cv::Mat M;
        M.create(5, 4, CV_8UC4);//创建2维矩阵对象
        //注意:这种方法好像不能有第四个颜色参数,每个点的颜色随机
    
        std::cout << M << std::endl;
        cv::Mat M = cv::Mat::eye(4, 4, CV_32F);  //创建单位矩阵
        std::cout << M << std::endl;

        cv::Mat M = cv::Mat::ones(4, 4, CV_32F);  //创建全是1的矩阵
        std::cout << M << std::endl;

        cv::Mat M = cv::Mat::zeros(4, 4, CV_32F);  //创建全是0的矩阵
        std::cout << M << std::endl;

        cv::Mat M = (cv::Mat_<double>(3, 3) << 0, -10, 0, -11, 0, 0, 0, 88, 1);  //创建自定义数据的矩阵
        std::cout << M << std::endl;
        cv::Mat M = (cv::Mat_<double>(3, 3) << 0, -10, 0, -11, 0, 0, 0, 88, 1); 
        cv::Mat M5 = M.row(1).clone(); //M5中的数据就是M的第二行数据
        //通过克隆函数clone获取我们需要的某一行或列的数据,这里构建出来的矩阵是深拷贝出来的Mat类对象
        std::cout << M5 << std::endl;

    Mat基本属性

        cv::Mat A = cv::imread("D:/bb/tu/ma.jpg",1);
        int i = A.type();//返回图像属性
        //具体对应值见下表
        std::cout<< i;
        
        cv::namedWindow("显示");
        imshow("显示",A);

        cv::Mat A = cv::imread("D:/bb/tu/ma.jpg",1);
        int i = A.channels();  //返回通道数
        int w=A.cols; //返回列数,即宽
        int h=A.rows; //返回行数,即高
    
        cv::namedWindow("显示");
        imshow("显示",A);
    
        qDebug()<<i<<w<<h;
    cv::Mat sm(6, 5, CV_8UC3);
    
    int d=sm.depth();//获取矩阵元素深度,其返回的其类型和Mat一致
    /* 返回值对应的元素深度
    CV_8U   = 0 - 8-bit unsigned integers ( 0..255 )
    CV_8S   = 1 - 8-bit signed integers ( -128..127 )
    CV_16U  = 2 - 16-bit unsigned integers ( 0..65535 )
    CV_16S  = 3 - 16-bit signed integers ( -32768..32767 )
    CV_32S  = 4 - 32-bit signed integers ( -2147483648..2147483647 )
    CV_32F  = 5 - 32-bit floating-point numbers ( -FLT_MAX..FLT_MAX, INF, NAN )
    CV_64F  = 6 - 64-bit floating-point numbers ( -DBL_MAX..DBL_MAX, INF, NAN )
    CV_USRTYPE1=7
    */
    
    int c=sm.channels(); //返回矩阵通道数目
    int dim=sm.dims;  //返回矩阵维度
    int e=sm.elemSize();//返回每个元素占用的字节数大小(带通道)
    int e1=sm.elemSize1();//返回单个元素值占用的字节数大小
    int w=sm.step[0];  //第一级在矩阵内存中占据的字节的数量
    //step[i]就是第i+1级在矩阵内存中占据的字节的数量
    //资料看:https://blog.csdn.net/lanmeng_smile/article/details/47864615
    
    
    int h=sm.step1(1);  //一个元素所占的字节数
    
    std::cerr<<d<<std::endl;

  • 相关阅读:
    Xcode 统计代码行数
    AWS 根用户MFA丢失后如何处理
    istio 基础入门
    AWS 如何挑选合适EC2实例类型
    word去除页眉首页横线
    word 题注 图注 表注 交叉引用 自动编号
    (转)Python基础热图-参数超级详解
    VScode 运行代码显示:Code is already running!
    pyside2安装避坑
    vscode import numpy error:DLL load failed: The specific module could not be found
  • 原文地址:https://www.cnblogs.com/liming19680104/p/15368012.html
Copyright © 2020-2023  润新知