腐蚀和膨胀是形态学处理图像的基础。许多形态学算法都是以这两种原始操作作为基础的。
腐蚀
假设我们有一个图像A,以及一个结构元B(通常是矩形或者圆形)。一个结构元中定义一个中心点,B对A的腐蚀就是将结构元B滑过图像A,在图像A中完全包含B的区域。如下图所示:
图像A和结构元B以及腐蚀后的图像分别如下:
膨胀
膨胀和腐蚀相反,即B对A的膨胀为,结构元B滑过图像A,膨胀后的图像为所有与结构元B有重叠的图像。如下图所示:
图像的腐蚀和膨胀问题很容易利用opencv来实现,我们可以分别通过erode和dilate函数来实现,如下所示:
erode( src, erosion_dst, kernel );
dilate( src, dilation_dst, kernel );
第一个参数是原图像,第二个参数是输出图像,第三个参数为定义的结构元。
结构元我们可以通过getStructuringElement函数来获得,如下所示:
kernel = getStructuringElement( MORPH_ELLIPSE, Size( 5, 5 ), Point( 2, 2 ) );
第一个参数为结构元的类型,常用的有:
- 矩形: MORPH_RECT
- 交叉形: MORPH_CROSS
- 椭圆形: MORPH_ELLIPSE
完整实例
#include "opencv2\core\core.hpp"
#include "opencv2\imgproc\imgproc.hpp"
#include "opencv2\highgui\highgui.hpp"
#include <iostream>
using namespace cv;
using namespace std;
int main( int argc, char ** argv )
{
Mat src;
if( argc != 2 )
{
cerr << "参数个数错误!" << endl;
return -1;
}
src = imread( argv[1] );
if( !src.data )
{
cerr << "图像加载失败!" << endl;
return -1;
}
namedWindow( "src image", CV_WINDOW_AUTOSIZE );
namedWindow( "Erosion", CV_WINDOW_AUTOSIZE );
namedWindow( "Dilation", CV_WINDOW_AUTOSIZE );
imshow( "src image", src );
Mat kernel, erosion_dst, dilation_dst;
kernel = getStructuringElement( MORPH_ELLIPSE, Size( 5, 5 ), Point( 2, 2 ) );
erode( src, erosion_dst, kernel );
dilate( src, dilation_dst, kernel );
imshow( "Erosion", erosion_dst );
imshow( "Dilation", dilation_dst );
waitKey( 0 );
return 0;
}
运行结果: