学OpenCV

================================================

颜色模型之间可以互相转换

================================================

书中代码,对于通道的数据类型,用的固定值,实际上应当计算出来

1     int type = img.type();
2     int channel = CV_MAT_CN(type);//获得channel个数
3     int type_val = type & CV_MAT_DEPTH_MASK;//获得数据类型
4     cv::Mat mat0 = cv::Mat::zeros(img.rows, img.cols, CV_MAKETYPE(type_val,1));//确定数据类型和channel数

================================================

 示例代码

  1 #include <iostream>
  2 
  3 #include <opencv2/opencv.hpp>
  4 #include <opencv2/core/utils/logger.hpp>
  5 
  6 #include <vector>
  7 #include <string>
  8 
  9 void Test1()
 10 {
 11     cv::Mat img;
 12     img = cv::imread(R"(C:\testNoGit\learnOpenCV4-master\data\lena.png)");
 13     if (img.empty())
 14     {
 15         std::cout << "请确认图像文件名是否正确" << std::endl;
 16         return ;
 17     }
 18 
 19     std::vector<cv::Mat> vctMatChannel;
 20     cv::split(img, vctMatChannel);
 21 
 22     int num = vctMatChannel.size();
 23 
 24     for (int i = 0; i < num; i++)
 25     {
 26         std::string strCaption = std::string("Test1 channel ") + std::to_string(i);
 27         
 28         cv::imshow(strCaption, vctMatChannel[i]);
 29     }
 30 
 31     //cv::Mat mat0 = cv::Mat::zeros(img.rows, img.cols,CV_8UC1);//其实最好还是先确定原图的数据类型
 32 
 33     int type = img.type();
 34     int channel = CV_MAT_CN(type);//获得channel个数
 35     int type_val = type & CV_MAT_DEPTH_MASK;//获得数据类型
 36     cv::Mat mat0 = cv::Mat::zeros(img.rows, img.cols, CV_MAKETYPE(type_val,1));//确定数据类型和channel数
 37 
 38     vctMatChannel[0] = mat0;//BGR
 39     vctMatChannel[1] = mat0;//BGR
 40     cv::Mat mat00R;
 41     cv::merge(vctMatChannel, mat00R);
 42     cv::imshow("Test1 00R", mat00R);
 43 
 44     vctMatChannel.push_back(mat0);
 45     cv::Mat mat00R0;
 46     cv::merge(vctMatChannel, mat00R0);
 47     cv::imshow("Test1 00R0", mat00R0);
 48 
 49     vctMatChannel.push_back(mat0);
 50     cv::Mat mat00R00;
 51     cv::merge(vctMatChannel, mat00R00);
 52     //cv::imshow("Test1 00R00", mat00R00);//imshow崩溃。因为通常RGBA最多是4通道,因此多于4通道崩溃。
 53 
 54     switch (type_val)
 55     {
 56     case CV_8U:std::cout << "CV_8U" << std::endl; break;
 57     case CV_8S:std::cout << "CV_8S" << std::endl; break;
 58     case CV_16U:std::cout << "CV_16U" << std::endl; break;
 59     case CV_16S:std::cout << "CV_16S" << std::endl; break;
 60     case CV_32S:std::cout << "CV_32S" << std::endl; break;
 61     case CV_32F:std::cout << "CV_32F" << std::endl; break;
 62     case CV_64F:std::cout << "CV_64F" << std::endl; break;
 63     default:std::cout << "UNKNOWN TYPE" << std::endl; break;
 64     }
 65 }
 66 
 67 void Test2()
 68 {
 69     cv::Mat img;
 70     img = cv::imread(R"(C:\testNoGit\learnOpenCV4-master\data\lena.png)");
 71     if (img.empty())
 72     {
 73         std::cout << "请确认图像文件名是否正确" << std::endl;
 74         return;
 75     }
 76 
 77     int num =img.channels();
 78     cv::Mat* arrMatChannel = new cv::Mat[num];
 79     cv::split(img, arrMatChannel);
 80 
 81 
 82     for (int i = 0; i < num; i++)
 83     {
 84         std::string strCaption = std::string("Test2 channel ") + std::to_string(i);
 85 
 86         cv::imshow(strCaption, arrMatChannel[i]);
 87     }
 88 
 89     cv::Mat mat0 = cv::Mat::zeros(img.rows, img.cols, CV_8UC1);
 90     arrMatChannel[0] = mat0;//BGR
 91     arrMatChannel[1] = mat0;//BGR
 92     cv::Mat mat00R;
 93     cv::merge(arrMatChannel,num, mat00R);
 94     cv::imshow("Test2 00R", mat00R);
 95 }
 96 
 97 int main()
 98 {
 99     cv::utils::logging::setLogLevel(cv::utils::logging::LOG_LEVEL_ERROR);
100     
101     Test1();
102     Test2();
103 
104     cv::waitKey(0);
105 
106     return 0;
107 }

 

================================================

查看效果

================================================

多于4通道无法用imshow查看,可以在image show里以数据的形式查看