zoukankan      html  css  js  c++  java
  • 004 :opencv 中矩阵操作以及通过内存的方式取像素

     1.以下代码是对于矩阵和像素运算总结

    #include <iostream>
    #include <string>
    #include <sstream>
    using namespace std;
    
    // OpenCV includes
    #include "opencv2/core/utility.hpp"
    #include "opencv2/imgproc.hpp"
    #include "opencv2/highgui.hpp"
    using namespace cv;
    
    // OpenCV command line parser functions
    // Keys accecpted by command line parser
    const char* keys =
    {
        "{help h usage ? | | print this message}"
        "{@sample |0 | Sample number to show}"
    };
    
    
    int main( int argc, const char** argv )
    {
        CommandLineParser parser(argc, argv, keys);
        parser.about("Chapter 2. v1.0.0");
        //If requires help show
        if (parser.has("help"))
        {
            parser.printMessage();
            return 0;
        }
    
        int sample= parser.get<int>(0);
    
        // Check if params are correctly parsed in his variables
        if (!parser.check())
        {
            parser.printErrors();
            return 0;
        }
    
    
        switch(sample)
        {
            case 0:
            {    cout << "Sample 0, Mat zeros" << endl;
                Mat m= Mat::zeros(5,5, CV_32F);//元素全部为0的矩阵
                cout << m << endl;
                break;
            }
            case 1:
            {    cout << "Sample 0, Mat ones" << endl;
                Mat m= Mat::ones(5,5, CV_32F);//元素全部为1的矩阵
                cout << m << endl;
                break;
            }
            case 2:
            {    cout << "Sample 0, Mat eye" << endl;
                Mat m= Mat::eye(5,5, CV_32F); //单位矩阵
                cout << m << endl;
    
                Mat a= Mat::eye(Size(3,2), CV_32F);
                Mat b= Mat::ones(Size(3,2), CV_32F);
                Mat c= a+b;                    //矩阵相加
                Mat d= a-b;                    //矩阵相加
                cout << a << endl;
                cout << b << endl;
                cout << c << endl;
                cout << d << endl;
                break;
            }
            case 3:
            {    cout << "Sample 0, Mat operations:" << endl;
                Mat m0= Mat::eye(3,3, CV_32F);
                m0=m0+Mat::ones(3,3, CV_32F);
                Mat m1= Mat::eye(2,3, CV_32F);
                Mat m2= Mat::ones(3,2, CV_32F);
    
                cout << "
    m0
    " << m0 << endl;
                cout << "
    m1
    " << m1 << endl;
                cout << "
    m2
    " << m2 << endl;
                
    
                cout << "
    m1.*2
    " << m1*2 << endl;        //矩阵与标量相乘,每一个元素都乘以该标量
                cout << "m1+3" << m1 + 3 << endl;            //矩阵与标量相乘,每一个元素都加上该标量
                cout << "
    (m1+2).*(m1+3)
    " << (m1+1).mul(m1+3) << endl;//矩阵相乘
                cout << "
    m1*m2
    " << m1*m2 << endl;//矩阵相乘
                cout << "
    t(m2)
    " << m2.t() << endl;//矩阵转置
                cout << "
    inv(m0)
    " << m0.inv() << endl;//矩阵求逆  前提矩阵必须可逆
                break;
            }
            case 4:
            {
                Mat image= imread("lena.jpg", 0);
                int myRow=511;
                int myCol=511;
    
                uchar* ptr1 = (image.data + myRow * image.cols*image.channels() + myCol);///通过uchar获取对应的像素地址
                int val1=*(image.data+myRow*image.cols*image.channels()+ myCol);
                cout << "Pixel value:(511,511)" << val1 << endl;
                int endRow = 0;
                int endCol = 0;
                int val2 = *(image.data + endRow * image.cols*image.channels() + endCol);
                cout << "END Pixel value:(512,512)" << val2 << endl;
                endRow = 1;
                endCol = 1;
                int val3 = *(image.data + endRow * image.cols*image.channels() + endCol);
                cout << "END Pixel value:(1,1)" << val3 << endl;
                int startRow = 512;
                int startCol = 512;
                 uchar* ptr2 = (image.data + startRow * image.cols*image.channels() + startCol);///通过uchar获取对应的像素地址
    
                int val4 = *(image.data + startRow * image.cols*image.channels() + startCol);
                cout << "Start Pixel value:(512,512)" << val4 << endl;
                Mat Bimage = imread("lena.jpg", 1);
                endRow = 1;
                endCol = 1;
                int val5 = *(Bimage.data + endRow * Bimage.cols*Bimage.channels() + endCol);
                cout << "END G Pixel value:(1,1)" << val5 << endl;
    
    
    
                imshow("Lena", image);
                waitKey(0);
                break;
            }
            case 5:
            {
                Mat image= imread("lena.jpg");
                int myRow=511;
                int myCol=511;
                int B=*(image.data+myRow*image.cols*image.channels()+ myCol + 0);
                int G=*(image.data+myRow*image.cols*image.channels()+ myCol + 1);
                int R=*(image.data+myRow*image.cols*image.channels()+ myCol + 2);
                cout << "Pixel value (B,G,R): (" << B << "," << G << "," << R << ")" << endl;
                imshow("Lena", image);
                waitKey(0);
                break;
            }
            case 6:
            {
                Vec<double,19> myVector;
                for(int i=0; i<19; i++){
                    myVector[i]= i;
                }
                cout << myVector << endl;
    
            }
        }
    
        return 0;
    
    }

    2。直接获取像素内存地址,访问内存地址

        单通道的图像的访问第(Row,Col)的像素的灰度值方式

      访问单个通道的图像(Row,Col)位置的像素指针为(注意图像矩阵的索引是从(0,0)开始的

      uchar * ptr = image.data(图像的指针)+Row*image.cols(图像的Col数量)*image.channels(图像的通道数量1)+Col

     访问多通道中的第n个通道(注意通道是从0开始的

     uchar * ptr = image.data(图像的指针)+Row*image.cols(图像的Col数量)*image.channels(图像的通道数量1)+Col+n

        

     3.查看vs2017中的指针对应的的数据的方式。

      通过调试——》窗口——》内存——》内存块1/2/3/4(这里每一次调试系统给分配的内存地址的位置可能不同)

    这事界面上会出现一个窗口,显示内存中的数据。

    但是为什么通过(512,512)的位置也会取到值呢,不应该报数组越界吗?跟踪了下对应的512,512的指针的位置,确实值为dd,即是221,说明mat 结构在尾部还有一部分数据。

    内存调试的问题,什么后面在内存中看不到我需要的指针数据呢?有我有疑问~~~~

  • 相关阅读:
    利用dockerfile定制镜像
    发布Docker 镜像到dockerhub
    Docker 停止容器
    133. Clone Graph
    132. Palindrome Partitioning II
    131. Palindrome Partitioning
    130. Surrounded Regions
    129. Sum Root to Leaf Numbers
    128. Longest Consecutive Sequence
    127. Word Ladder
  • 原文地址:https://www.cnblogs.com/codeAndlearn/p/11562337.html
Copyright © 2011-2022 走看看