OpenCV 2.4.3 C++ 平滑处理分析

原理

平滑也称模糊, 是一项简单且使用频率很高的图像处理方法。

平滑处理时需要用到一个滤波器。 最常用的滤波器是线性滤波器,线性滤波处理的输出像素值(例如:)是输入像素值(例如:)的加权平均:

    

称为核, 它仅仅是一个加权系数。

均值平滑

下面是一个使用blur函数的均值平滑:


代码如下:

#include "opencv2/core/core.hpp"

#include "opencv2/highgui/highgui.hpp"

#include "opencv2/imgproc/imgproc.hpp"

#include <stdio.h>

using namespace cv;

int main( int argc, char** argv ){
Mat image;
image = imread( argv[1]);

if( argc != 2 || !image.data ){
printf("没有图片\n");
return -1;
}

namedWindow( "平滑处理-输入" );
namedWindow( "平滑处理-输出" );

imshow( "平滑处理-输入", image );

Mat out;

blur( image, out, Size(3, 3));

imshow( "平滑处理-输出", out );

waitKey( 0 );
}

blur函数API资料:

使用归一化块滤波器进行模糊图片操作。

C++: void blur(InputArray src, OutputArray dst, Size ksize, Point anchor=Point(-1,-1), int borderType=BORDER_DEFAULT ) 参数src – 输入图片,可以使是任意通道数,该函数对通道是独立处理的,但是深度只能是CV_8U, CV_16U, CV_16S, CV_32F or CV_64F。dst – 输出图片,和输入图片相同大小和深度。ksize – 模糊内核大小。anchor – 锚点,默认值是(-1,-1),也就是锚点在内核的中心。borderType – 用于判断图像边界的模式。

该函数对图片进行平滑处理利用了下面的内核:

调用blur(src, dst, ksize, anchor, borderType)相当于调用boxFilter(src, dst, src.type(), anchor, true, borderType)。

blur使用的是归一化块滤波器,输出像素值是核窗口内像素值的均值( 所有像素加权系数相等)。

高斯平滑

下面代码使用了GaussianBlur来实现平滑:


代码如下:

#include "opencv2/core/core.hpp"

#include "opencv2/highgui/highgui.hpp"

#include "opencv2/imgproc/imgproc.hpp"

#include <stdio.h>

using namespace std;
using namespace cv;int main( int argc, char** argv ){
Mat image;
image = imread( argv[1]);

if( argc != 2 || !image.data ){
printf("没有图片\n");
return -1;
}

namedWindow( "平滑处理-输入" );
namedWindow( "平滑处理-输出" );

imshow( "平滑处理-输入", image );

Mat out;

GaussianBlur( image, out, Size( 3, 3 ), 0, 0 );

imshow( "平滑处理-输出", out );

waitKey( 0 );
}

GaussianBlur函数API资料:

使用高斯滤波器进行模糊操作

C++: void GaussianBlur(InputArray src, OutputArray dst, Size ksize, double sigmaX, double sigmaY=0, int borderType=BORDER_DEFAULT) 参数 src – 输入图片,可以使是任意通道数,该函数对通道是独立处理的,但是深度只能是CV_8UCV_16UCV_16SCV_32F or CV_64F.dst – 输出图片,和输入图片相同大小和深度。ksize – 高斯内核大小。ksize.widthksize.height允许不相同但他们必须是正奇数。或者等于0,由参数sigma的乘机决定。sigmaX – 高斯内核在X方向的标准偏差。sigmaY – 高斯内核在Y方向的标准偏差。如果sigmaY为0,他将和sigmaX的值相同,如果他们都为0,那么他们由ksize.widthksize.height计算得出。borderType – 用于判断图像边界的模式。

最有用的滤波器 (尽管不是最快的)。 高斯滤波是将输入数组的每一个像素点与高斯内核卷积将卷积和当作输出像素值。

参考一维高斯函数,我们可以看见,他是个中间大两边小的函数。

所以高斯滤波器其加权数是中间大,四周小的。

其二维高斯函数为:

    

其中  为均值 (峰值对应位置), 代表标准差 (变量 和 变量 各有一个均值,也各有一个标准差)。

中值平滑

使用medianBlur执行中值平滑:


代码如下:

#include "opencv2/core/core.hpp"

#include "opencv2/highgui/highgui.hpp"

#include "opencv2/imgproc/imgproc.hpp"

#include <stdio.h>

using namespace std;
using namespace cv;int main( int argc, char** argv ){
Mat image;
image = imread( argv[1]);

if( argc != 2 || !image.data ){
printf("没有图片\n");
return -1;
}

namedWindow( "平滑处理-输入" );
namedWindow( "平滑处理-输出" );

imshow( "平滑处理-输入", image );

Mat out;
medianBlur( image, out, 3);

imshow( "平滑处理-输出", out );

waitKey( 0 );
}

medianBlur函数API资料:

使用中值滤波器进行模糊操作

C++: void medianBlur(InputArray src, OutputArray dst, int ksize) Parameters:src – 支持1、3、4通道图片输入,当ksize为3或者5时,图片的深度只能是CV_8U,,CV_16U,或者 CV_32F,对于其他大孔径尺寸只支持深度为CV_8U。dst – 输出图片,和输入图片相同大小和深度。ksize – 线性直径大小,只能是一个大于1的奇数,例如:3, 5, 7 ...

中值滤波将图像的每个像素用邻域 (以当前像素为中心的正方形区域)像素的中值代替 。

双边平滑

使用bilateralFilter执行双边平滑:


代码如下:

#include "opencv2/core/core.hpp"

#include "opencv2/highgui/highgui.hpp"

#include "opencv2/imgproc/imgproc.hpp"

#include <stdio.h>

using namespace std;
using namespace cv;int main( int argc, char** argv ){
Mat image;
image = imread( argv[1]);

if( argc != 2 || !image.data ){
printf("没有图片\n");
return -1;
}

namedWindow( "平滑处理-输入" );
namedWindow( "平滑处理-输出" );

imshow( "平滑处理-输入", image );

Mat out;
bilateralFilter ( image, out, 3, 3*2, 3/2 );

imshow( "平滑处理-输出", out );

waitKey( 0 );
}

bilateralFilter的API资料:

对一个图片应用双边滤波器。

C++: void bilateralFilter(InputArray src, OutputArray dst, int d, double sigmaColor, double sigmaSpace, intborderType=BORDER_DEFAULT ) Parameters:src – 源必须是8位或者浮点数,1或者3通道图片。dst – 输出图片,和输入图片相同大小和深度。d – 在滤波过程中使用的各像素邻域直径,如果这是一个非整数,则这个值由sigmaSpace决定。sigmaColor – 颜色空间的标准方差。数值越大,意味着越远的的颜色会被混进邻域内,从而使更大的颜色段获得相同的颜色。sigmaSpace – 坐标空间的标注方差。 数值越大,以为着越远的像素会相互影响,从而使更大的区域足够相似的颜色获取相同的颜色。当d>0,d指定了邻域大小且与sigmaSpace无关。否则,d正比于sigmaSpace

原理可参考

http://www.dai.ed.ac.uk/CVonline/LOCAL_COPIES/MANDUCHI1/Bilateral_Filtering.html

目前我们了解的滤波器都是为了平滑图像, 问题是有些时候这些滤波器不仅仅削弱了噪声, 连带着把边缘也给磨掉了。 为避免这样的情形 (至少在一定程度上 ), 我们可以使用双边滤波。

类似于高斯滤波器,双边滤波器也给每一个邻域像素分配一个加权系数。 这些加权系数包含两个部分, 第一部分加权方式与高斯滤波一样,第二部分的权重则取决于该邻域像素与当前像素的灰度差值。

(0)

相关推荐

  • 基于C++实现kinect+opencv 获取深度及彩色数据

    开发环境 vs2010+OPENCV2.4.10 首先,下载最新的Kinect 2 SDK  http://www.microsoft.com/en-us/kinectforwindows/develop/downloads-docs.aspx 下载之后不要插入Kinect,最好也不用插入除了键盘鼠标以外的其它USB设备,然后安装SDK,安装完成之后插入Kinect,会有安装新设备的提示.安装完成之后可以去"开始"那里找到两个新安装的软件,一个是可以显示Kinect深度图,另外一个软件

  • OpenCV中C++函数imread读取图片的问题及解决方法

    今天在用OpenCV实验Image Pyramid的时候发现一个奇怪的问题,就是利用C++函数imread读取图片的时候返回的结果总是空,而利用C函数cvLoadImage时却能读取到图像.代码如下: //环境:VS2010 + OpenCV 2.3.1 #include "stdafx.h" #include <cv.h> #include <highgui.h> #include <math.h> #include <stdlib.h>

  • OpenCV 2.4.3 C++ 平滑处理分析

    原理 平滑也称模糊, 是一项简单且使用频率很高的图像处理方法. 平滑处理时需要用到一个滤波器. 最常用的滤波器是线性滤波器,线性滤波处理的输出像素值(例如:)是输入像素值(例如:)的加权平均: 称为核, 它仅仅是一个加权系数. 均值平滑 下面是一个使用blur函数的均值平滑: 复制代码 代码如下: #include "opencv2/core/core.hpp" #include "opencv2/highgui/highgui.hpp" #include &quo

  • opencv实现轮廓高斯滤波平滑

    本文实例为大家分享了opencv实现轮廓高斯滤波平滑的具体代码,供大家参考,具体内容如下 一个小测试的题目: 在图像上点选,找到与点选处相邻的颜色相近的点集合,对该点集合提取轮廓,对该点集合轮廓平滑处理,显示处理结果. #include <opencv2/opencv.hpp> #include <iostream> using namespace std; using namespace cv; //************************************ //

  • 详解OpenCV执行连通分量标记的方法和分析

    目录 1.OpenCV 连通分量标记和分析 1.1 OpenCV 连通分量标记和分析函数 1.2 项目结构 2.案例实现 2.1 使用 OpenCV 实现基本的连通分量标记 2.2 完整代码 2.3 过滤连通分量 2.4 C++代码案例 在本教程中,您将学习如何使用 OpenCV 执行连通分量标记和分析.具体来说,我们将重点介绍 OpenCV 最常用的连通分量标记函数:cv2.connectedComponentsWithStats. 连通分量标记(也称为连通分量分析.斑点提取或区域标记)是图论

  • Python3+OpenCV实现简单交通标志识别流程分析

    由于该项目是针对中小学生竞赛并且是第一次举行,所以识别的目标交通标志仅仅只有直行.右转.左转和停车让行. 数据集: 链接: https://pan.baidu.com/s/1SL0qE-qd4cuatmfZeNuK0Q 提取码: vuvi  源代码:https://github.com/ccxiao5/Traffic_sign_recognition 整体流程如下: 数据集收集(包括训练集和测试集的分类) 图像预处理 图像标注 根据标注分割得到目标图像 HOG特征提取 训练得到模型 将模型带入识

  • visual studio 2013中配置opencv图文教程 Opencv2.4.9安装配置教程

    Opencv2.4.9安装和在visualstudio 2013中配置 下载opencv和在windows下安装: 最新版本号的opencv是2014.4.25的opencv2.4.9,这里选择当前最新版本号. 点击opencv for windows就可以下载. 下载完毕后.双击图标 会出现以下的提示框 选择你要将opencv保存的位置,提取内部文件. 我这里将opencv保存在视频分析入门联系目录下.(提醒,opencv提取后.大小为3.7G,所以确保有足够的空间) Build目录内是经过编

  • opencv 做人脸识别 opencv 人脸匹配分析

    机器学习 机器学习的目的是把数据转换成信息. 机器学习通过从数据里提取规则或模式来把数据转成信息. 人脸识别 人脸识别通过级联分类器对特征的分级筛选来确定是否是人脸. 每个节点的正确识别率很高,但正确拒绝率很低. 任一节点判断没有人脸特征则结束运算,宣布不是人脸. 全部节点通过,则宣布是人脸. 工业上,常用人脸识别技术来识别物体. 对图片进行识别 复制代码 代码如下: #include "opencv2/core/core.hpp" #include "opencv2/obj

  • python 基于opencv实现高斯平滑

    假设一个列数为W,行数为H的高斯卷计算子gaussKernel,其中W,H均为奇数,描点位置在((H-1)/2 ,(W-1)/2),构建高斯卷积核的步骤如下 1.计算高斯矩阵 2.计算高斯矩阵的和 3.高斯矩阵除以其本身的和,也就是归一化 下面利用Python来实现构建高斯卷积算子 def getGaussKernel(sigma, H, W): r, c = np.mgrid[0:H:1, 0:W:1] r -= (H - 1) / 2 c -= (W - 1) / 2 gaussMatrix

  • python通过opencv调用摄像头操作实例分析

    实例源码: #pip3 install opencv-python import cv2 from datetime import datetime FILENAME = 'myvideo.avi' WIDTH = 1280 HEIGHT = 720 FPS = 24.0 # 必须指定CAP_DSHOW(Direct Show)参数初始化摄像头,否则无法使用更高分辨率 cap = cv2.VideoCapture(0, cv2.CAP_DSHOW) # 设置摄像头设备分辨率 cap.set(cv

  • OpenCV NAO机器人辅助捡球丢球流程分析

    目录 1. 概述 2. 相关技术 2.1 NAO机器人 2.2 Choregraphe 3. 总体设计与详细设计 3.1 系统模块划分 3.2 主要功能模块 4 视频展示 1. 概述 NAO机器人身高58cm,体重5.4kg.主要硬件包括CPU.主板.扬声器.话筒.红外线.相机.超声波(声呐).传感器.电机.语音合成器.陀螺仪等.实验室中NAO机器人的型号为NAOH25,其构造如下: NAO机器人的操作系统为Gentoo Linux,它支持Windows.Linux.Mac OS等操作系统的远程

  • OpenCV视频流C++多线程处理方法详细分析

    目录 为什么需要多线程处理视频流 C++的多线程处理方式 函数封装的实现方式 类封装的实现方式 可能遇到的问题 为什么需要多线程处理视频流 在之前有写过一篇文章Python环境下OpenCV视频流的多线程处理方式,上面简单记录了如何使用Python实现对OpenCV视频流的多线程处理.简单来说,在目标检测等任务中,如果视频流的捕获.解码以及检测都在同一个线程中,那么很可能出现目标检测器实时性不高导致的检测时延问题.使用多线程处理,将视频帧的捕获和解码放在一个线程,推理放在一个线程,可以有效缓解时

随机推荐