openCV中Mat类对象以深拷贝方式存放到容器中,避免造成数据混乱

首先拿到一张图片,通过split()函数把图像的RGB值分别拿出来存到到一个vector容器中,然后以灰度图像(即单通道)的形式分别输出R,G,B的值,再把R,G,B的值单独以彩色图像(三通道)的形式输出,达到下图的效果

 写出代码如下:

int main()
{
    Mat image = imread("F:/cv/1.bmp");
	imshow("原图像", image);

	std::vector<Mat> mv;//存储分离后的管道
	split(image, mv); // 管道分离
	imshow("蓝色通道", mv[0]);
	imshow("绿色通道", mv[1]);
	imshow("红色通道", mv[2]);

	std::vector<Mat> blue(mv);
	std::vector<Mat> green(mv);
	std::vector<Mat> red(mv);

	Mat dst;//存储输出图像

	blue[1] = 0;
	blue[2] =0;
	merge(blue, dst);
	imshow("蓝色图像", dst);

	green[0] = 0;
	green[2] =0;
	merge(green, dst);
	imshow("绿色图像", dst);

	red[0] = 0;
	red[1] = 0;
	merge(red, dst);
	imshow("红色图像", dst);
}

上述代码创建一个容器对象mv存储分离后的通道值,mv[0] -> 蓝色,mv[1] -> 绿色,mv[2] -> 红色.

如果要以彩色图像分别输出图像的B,G,R值,再创建三个容器对象,blue,green,red.(此处创建方式有问题),要拿到blue的蓝色值,就要把红和绿全部过滤,代码实现为 (blue[1] = 0;    blue[2] = 0;),同理单独拿到green的绿色值,red的红色值,之后通过merge()函数合并三个通道的值,输出,结果却出了问题

 输出的红色图像和绿色图像全为黑色,这是因为创建容器对象blue,green,red的时候出了问题

	std::vector<Mat> blue(mv);
	std::vector<Mat> green(mv);
	std::vector<Mat> red(mv);

        因为Mat类并不是像int一样,是系统自带的数据类型,所以这种创建方式会调用vector的默认拷贝构造,即浅拷贝。造成的结果就是这个三个容器对象数据完全共享,这三个对象都指向mv,所以第一次输出彩色图像时可以正常输出,但第二次输出绿色图像时,green[1]的值已经全被 blue[1]=0; 的操作全被改为了0,此时只有green[0]还正常存储图像的蓝色值,但是后面的代码把蓝色值也赋值为0,最终导致这三个矩阵green[0],green[1],green[2]都是0,然后就输出了纯黑图像,代码运行到red,自然也是纯黑。

所以我们要创建三个相互独立的容器对象blue,green,red,只需把原来用来创建的的三行代码替换为下面的内容:

	std::vector<Mat> blue;//蓝
	for (const Mat& m : mv)
	{
		blue.push_back(m.clone());
	}
	std::vector<Mat> green;
	for (const Mat& m : mv)//绿
	{
		green.push_back(m.clone());
	}
	std::vector<Mat> red;//红
	for (const Mat& m : mv)
	{
		red.push_back(m.clone());
	}

 此处使用枚举循环进行构造,参考此文:(4条消息) C++:枚举循环,全局作用域,子类调用父类函数,const类成员赋值_头发乌黑茂密的博客-CSDN博客

创建的每个容器对象,都是通过mv的克隆函数构造的,彼此相互独立(也可以使用copyTo函数),这样就可以达到我们的目的了。

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

头发乌黑茂密

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值