opencv3.1.0+vs2015——矩阵的掩模操作和自定义线性滤波

(一)矩阵的掩模操作

掩模操作实现图像对比度调整
红色是中心像素,从上到下,从左到右对每个像素做同样的处理操作,得到最终结果就是对比度提高之后的输出图像Mat对象。
I(i,j)=5*I(i.j)-[I(i-1,j)+I(i+1,j)+I(i,j-1)+I(i,j+1)]
在这里插入图片描述   在这里插入图片描述
1.定义掩模:Mat kernel=(Mat_< char >(3,3)<<0,-1,0,-1,5,-1,0,-1,0);
2.filter2D(src,dst,src.depth(),kernel);其中src与dst是Mat类型变量、src.depth表示位图深度,有32、24、8等,若为-1默认为与src深度相等。
在这里插入图片描述

#include<opencv2/opencv.hpp>
#include<iostream>
using namespace cv;
int main(int argc,char** argv)
{
	Mat src, dst;
	src = imread("D:/studytest/lena.jpg");   //读取一张图片
	if (!src.data)
	{
		printf("could not load image...\n");
		return -1;
	}
	namedWindow("input_image", CV_WINDOW_AUTOSIZE);
	imshow("input_image", src);   //显示一张图
	//row行 col列
	/*int cols = (src.cols-1)*src.channels(); 
	int offsetx = src.channels();
	int rows = src.rows;
	dst = Mat::zeros(src.size(), src.type());
	for (int row = 1; row < rows - 1; row++)
	{
		const uchar* previous = src.ptr<uchar>(row - 1); //指针previous指向src的row-1行
		const uchar* current = src.ptr<uchar>(row);  //指针current指向src的row行
		const uchar* next = src.ptr<uchar>(row + 1); //指针next指向src的row+1行
		uchar* output = dst.ptr<uchar>(row); //指针output指向dst的row行
		for (int col = offsetx; col < cols; col++)
		{
			output[col] =saturate_cast<uchar>( 5 * current[col] - (current[col - offsetx] + current[col + offsetx] + previous[col] + next[col])); //saturate_cast将小于0的置为0,将大于255的置为255,其余为原值
		}
	}*/
	//上面注释掉的代码块与下面的掩模操作一样
	double t = getTickCount(); //开始时间
	Mat kernel = (Mat_<char>(3, 3) << 0, -1, 0, -1, 5, -1, 0, -1, 0);//掩模
	filter2D(src, dst, src.depth(), kernel);//filter2D(src, dst, -1, kernel);  -1默认为和原图深度一样
	double timeconsume = (getTickCount() - t) / getTickFrequency(); //时间消耗
	printf("time consume %.2f", timeconsume);
	namedWindow("contract image demo", CV_WINDOW_AUTOSIZE);
	imshow("contract image demo", dst);
	waitKey(0);
	return 0;
}

显示结果如下图所示:
在这里插入图片描述

(二)自定义线性滤波

在这里插入图片描述

#include<opencv2/opencv.hpp>
#include<iostream>
using namespace std;
using namespace cv;
int main(int argc, char** argv)
{
	Mat src;
	src = imread("D:/studytest/lena.jpg");
	if (src.empty())
	{
		printf("could not load image...\n");
		return -1;
	}
	namedWindow("input image", CV_WINDOW_AUTOSIZE);
	imshow("input image", src);
	Mat Robx, Roby,Sobx,Soby,lap;
	//Robert X方向
	Mat kernel_rx = (Mat_<int>(2, 2) << 1, 0, 0, -1);
	filter2D(src, Robx, -1, kernel_rx, Point(-1, -1), 0, 0);
	imshow("robert_x image", Robx);
	//Robert Y方向
	Mat kernel_ry = (Mat_<int>(2, 2) << 0, 1, -1, 0);
	filter2D(src, Roby, -1, kernel_ry, Point(-1, -1), 0, 0);
	imshow("robert_y image", Roby);
	//Sobel X方向
	Mat kernel_sx = (Mat_<int>(3, 3) << -1, 0, 1, -2, 0, 2, -1, 0, 1);
	filter2D(src, Sobx, -1, kernel_sx, Point(-1, -1), 0, 0);
	imshow("Sobel_x image", Sobx);
	//Sobel Y方向
	Mat kernel_sy = (Mat_<int>(3, 3) << -1, -2, -1, 0, 0, 0, 1, 2, 1);
	filter2D(src, Soby, -1, kernel_sy, Point(-1, -1), 0, 0);
	imshow("Sobel_y image", Soby);
	//拉普拉斯算子
	Mat kernel_lap = (Mat_<int>(3, 3) << 0, -1, 0, -1, 4, -1, 0, -1, 0);
	filter2D(src, lap, -1, kernel_lap, Point(-1, -1), 0, 0);
	imshow("lap image", lap);
	//自定义卷积核来实现模糊
	int c = 0;
	int index = 0;
	int ksize = 0;
	Mat dst;
	while (true)
	{
		c=waitKey(500);
		if ((char)c == 27)//键盘上对应ESC
			break;
		ksize = 4+(index%5)*2+1;
		Mat kernel = Mat::ones(Size(ksize, ksize), CV_32F)/(float)(ksize*ksize);
		filter2D(src, dst, -1, kernel, Point(-1, -1));
		index++;
		imshow("output image", dst);
	}
	return 0;
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值