本文是对OpenCV2.4.13文档的部分翻译,作个人学习之用,并不完整。
卷积:广义上就是在一个操作器(核)与图像每一部分之间的操作。
核:核就是一个固定大小的数字系数数组,并且在数组中有一个锚点,通常是在中心位置。
用核做卷积操作:假设想要知道图像中特定位置的结果值,卷积值可以这样计算:
1.将核的锚点置于某个像素上,用核的其余位置来覆盖相应的周围像素
2.用对应的图像像素值乘以核的系数求和得到结果
3.将结果置于输入图像的锚点位置
4.通过扫描整个图像对所有像素重复这个过程
OpenCV提供filter2D函数
#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/highgui/highgui.hpp"
#include <stdlib.h>
#include <stdio.h>
using namespace cv;
/**
* @function main
*/
int main ()
{
/// 声明变量
Mat src, dst;
Mat kernel;
Point anchor;
double delta;
int ddepth;
int kernel_size;
const char* window_name = "filter2D Demo";
int c;
/// 加载图像
src = imread("HappyFish.jpg");
if( !src.data )
{ return -1; }
/// 创建窗口
namedWindow( window_name, WINDOW_AUTOSIZE );
/// 为滤波器初始化参数
anchor = Point( -1, -1 );
delta = 0;
ddepth = -1;
/// 用有限循环来每0.5秒更新核的大小并对输入图像做线性变换
int ind = 0;
for(;;)
{
c = waitKey(500);
/// 'ESC'退出程序
if( (char)c == 27 )
{ break; }
/// 定义核与滤波器,用归一化块滤波器更新核大小
kernel_size = 3 + 2*( ind%5 );//每500ms更新核大小为[3,11]之间的奇数
kernel = Mat::ones( kernel_size, kernel_size, CV_32F )/ (float)(kernel_size*kernel_size);//设置各值为1的矩阵,通过元素数量划分来归一化建立核
/// 用filter2D函数生成滤波器:原图像、目标图像、目标图像的深度(一个负数如:-1,表示与原图深度相同)、用于扫描图像的核、
// 锚点相对于核的位置(-1,-1)就是中心位置(默认)、卷积时加到每个像素上的值(默认0)、最后一个就用默认(之后再讲)
filter2D(src, dst, ddepth , kernel, anchor, delta, BORDER_DEFAULT );
imshow( window_name, dst );
ind++;
}
return 0;
}
结果: