学习openCV之Mat类型访问每个像素

       网上关于mat类型的讲解很多,还有人将不同方式访问mat类型的时间打印出来,进行比较访问的快慢。但是我发现很多文章都是基于openCV中文论坛上的例子来写的(具http://www.opencv.org.cn/opencvdoc/2.3.2/html/doc/tutorials/core/how_to_scan_images/how_to_scan_images.html#howtoscanimagesopencv

,很少有单独说明如何访问每个像素的。本文以一个mat类型的例子来进行简单说明如何访问mat类型存储的图像。

        1、Mat类型中图像的存储方式

         彩色图片在计算机中是以每个像素对应有rgb值的方式存储的,灰度图片则是每个像素对应灰度值的方式存储的。反映在mat类型,彩色图片就是一个数组,用图片表示为:

 

即,每一个像素都是按照BGR的顺序进行存储。而灰度图片则直接按照坐标存储。

       2、访问Mat类型存储的图片

       首先读入一张彩色图片,然后将这张图片分别按照其R值、G值、B值获取对应的矩阵,并分别显示出来,代码如下:

<p>#include "stdafx.h" 
#include <opencv2/highgui/highgui.hpp> 
#include <opencv2\core\core.hpp></p><p>
#include <iostream></p><p>using namespace cv;
using namespace std;</p><p>int _tmain(int argc, _TCHAR* argv[])
{
 	Mat cmInPutImage = imread("E:\\openCV\\useMat\\resource\\baidu.jpg");</p><p>        //获取图片的通道数,灰度图片是单通道的,彩色图片一般是三通道
 	uchar nChannles = cmInPutImage.channels();</p><p> 	//获取图片的行和列数
 	unsigned int nRows = cmInPutImage.rows;
 	unsigned int nCols = cmInPutImage.cols;</p><p>
        //定义三个Mat类型的变量,分别用来存储R、G、B值,用0初始化
   	Mat cmOutPutR(nRows, nCols, CV_8UC(1), Scalar::all(0));
 	Mat cmOutPutG(nRows, nCols, CV_8UC(1), Scalar::all(0));
 	Mat cmOutPutB(nRows, nCols, CV_8UC(1), Scalar::all(0));</p><p>        //下面这个if语句是判断图片在内存中是不是连续存储的,如果是连续存储的,则在访问时可以连续的访问
        //-----------删除这几句也可以-----------//
 	if (cmInPutImage.isContinuous())
 	{
 		nCols *= nRows;
  		nRows = 1;
 	}</p><p>        //----------------结束----------------//</p><p> 
 
 
 	uchar *pSrc, *pDsR, *pDsG, *pDsB;</p><p> 	for (unsigned int i = 0; i < nRows; ++i)
 	{
  		pSrc = cmInPutImage.ptr<uchar>(i);</p><p>  		pDsR = cmOutPutR.ptr<uchar>(i);
  		pDsG = cmOutPutG.ptr<uchar>(i);
  		pDsB = cmOutPutB.ptr<uchar>(i);</p><p>  		for (unsigned int j = 0; j < nCols; ++j)
  		{
                         //注意在mat中是按照BGR的顺序存储的</p><p>          		pDsB[j] = pSrc[j*nChannles]; //访问B值
    			pDsG[j] = pSrc[j*nChannles+1]; //访问G值
     			pDsR[j] = pSrc[j*nChannles+2]; //访问R值
  		}
 	}</p><p> </p><p> 	cout<<"请选择"<<endl;
 	cout<<"1、输出原图;"<<endl;
 	cout<<"2、输出R图;"<<endl;
 	cout<<"3、输出G图;"<<endl;
 	cout<<"4、输出B图;"<<endl;</p><p> 	int a;
 	cin>>a;</p><p> 	if (1 == a)
 	{
  		imshow("原图", cmInPutImage);//显示原图
  	}
 	else if (2 == a)
 	{
  		imshow("R图", cmOutPutR);//显示R图
   	}
 	else if (3 == a)
 	{
  		imshow("G图", cmOutPutG);//显示G图
 	}
 	else
 	{
  		imshow("B图", cmOutPutB);//显示B图  
 	}</p><p> 	waitKey(60000);</p><p> 	return 0;
}
</p>

       3、显示效果

       
        

 

       转载请表明出处

 

 

 

 

 

 

 

 

            

 

      

  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值