OpenCV--形态学操作

图像形态学操作–基于形状的一系列图像处理操作的合集,主要是基于集合论基础上的形态学数学。
形态学有四个基本操作:膨胀、腐蚀、开、闭。
膨胀与腐蚀是图像处理中最常用的形态学操作手段。
膨胀与腐蚀都是对于高亮部分进行操作。
这里写图片描述

膨胀(dilation)

跟卷积操作类似,假设有图像A和结构元素B,结构元素B在A上面移动,其中B定义其中心为锚点,计算B覆盖下A的最大像素值来替换锚点的像素,其中B作为结构体可以是任意形状。
OpenCV提供的API:

Mat getStructuringElement(int shape, Size ksize, Point anchor=Point(-1,-1))//获取结构元素

void dilate(InputArray src, OutputArray dst, InputArray kernel, Point anchor=Point(-1,-1), int iterations=1, int borderType=BORDER_CONSTANT, const Scalar& borderValue=morphologyDefaultBorderValue())

实例代码:

int elementSize = 3;
int maxSize = 21;
char output_win[] = "膨胀后:";
Mat src,dest;
void CallBackFun(int,void*);

//膨胀操作
void DilateOper(){
    src = imread("1.png");
    if(!src.data){
        cout << "文件打开失败!" << endl;
        return ;
    }
    namedWindow("膨胀前",CV_WINDOW_AUTOSIZE);
    imshow("膨胀前",src);

    namedWindow(output_win,CV_WINDOW_AUTOSIZE);
    //创建滚动条
    createTrackbar("Size:",output_win,&elementSize,maxSize,CallBackFun);
    CallBackFun(0,0);

    cvWaitKey();
}

void CallBackFun(int,void*){
    int s = elementSize*2+1;
    /*
    getStructuringElement:
    第一个参数:选择结构元素的形状
        MORPH_RECT - a rectangular structuring element;
        MORPH_ELLIPSE - an elliptic structuring element;
        MORPH_CROSS - a cross-shaped structuring element;
        CV_SHAPE_CUSTOM - custom structuring element.
    */
    Mat kernel = getStructuringElement(MORPH_RECT,Size(s,s),Point(-1,-1));

    /*
    void dilate(InputArray src, OutputArray dst, InputArray kernel, Point anchor=Point(-1,-1), int iterations=1, int borderType=BORDER_CONSTANT, const Scalar& borderValue=morphologyDefaultBorderValue() )
    */
    dilate(src,dest,kernel);
    imshow(output_win,dest);

    return;
}

处理结果:
这里写图片描述


腐蚀

腐蚀操作和膨胀操作的过程类似,唯一不同的是一最小值替换锚点重叠下图像的像素值。

OpenCV提供的API:

void erode(InputArray src, OutputArray dst, InputArray kernel, Point anchor=Point(-1,-1), int iterations=1, int borderType=BORDER_CONSTANT, const Scalar& borderValue=morphologyDefaultBorderValue())   

实例代码:

//腐蚀操作
void ErodeOper(){
    src = imread("1.png");
    if(!src.data){
        cout << "文件打开失败!" << endl;
        return ;
    }
    namedWindow("腐蚀前",CV_WINDOW_AUTOSIZE);
    imshow("腐蚀前",src);

    namedWindow(output_win,CV_WINDOW_AUTOSIZE);
    //创建滚动条
    createTrackbar("Size:",output_win,&elementSize,maxSize,CallBackFun);
    CallBackFun(0,0);

    cvWaitKey();
}

void CallBackFun(int,void*){
    int s = elementSize*2+1;
    /*
    getStructuringElement:
    第一个参数:选择结构元素的形状
        MORPH_RECT - a rectangular structuring element;
        MORPH_ELLIPSE - an elliptic structuring element;
        MORPH_CROSS - a cross-shaped structuring element;
        CV_SHAPE_CUSTOM - custom structuring element.
    */
    Mat kernel = getStructuringElement(MORPH_RECT,Size(s,s),Point(-1,-1));

    /*
    void erode(InputArray src, OutputArray dst, InputArray kernel, Point anchor=Point(-1,-1), int iterations=1, int borderType=BORDER_CONSTANT, const Scalar& borderValue=morphologyDefaultBorderValue() )
    */
    erode(src,dest,kernel);
    imshow(output_win,dest);

    return;
}

处理结果:
这里写图片描述
很好的消除了小白点的干扰,但是主体还是有损失。


开操作

先腐蚀后膨胀
      在上面的腐蚀操作中,使用腐蚀虽然使早点消失,但是也使主体损失,这时我们可以再使用膨胀进行弥补。这一过程就是开操作。
OpenCV提供的API:

void morphologyEx(InputArray src, OutputArray dst, int op, InputArray kernel, Point anchor=Point(-1,-1), int iterations=1, int borderType=BORDER_CONSTANT, const Scalar& borderValue=morphologyDefaultBorderValue())
/*
部分参数介绍:
op:选择使用什么形态学操作
MORPH_OPEN - 开操作
MORPH_CLOSE - 闭操作
MORPH_GRADIENT - 形态学梯度
MORPH_TOPHAT - 顶帽
MORPH_BLACKHAT - 黑帽
MORPH_HITMISS - 击中与击不中
*/

实例代码:

void OpenOper(){
    src = imread("1.png");
    if(!src.data){
        cout << "文件打开失败!" << endl;
        return ;
    }
    namedWindow("开操作前",CV_WINDOW_AUTOSIZE);
    imshow("开操作前",src);

    //创建结构元素
    Mat kernel = getStructuringElement(MORPH_RECT,Size(7,7),Point(-1,-1));
    //执行开操作
    morphologyEx(src,dest,MORPH_OPEN,kernel);

    namedWindow("开操作后",CV_WINDOW_AUTOSIZE);
    imshow("开操作后",dest);

    cvWaitKey();
}

处理结果:
这里写图片描述
很好的消除了噪点,也使主体损失小。


闭操作

先膨胀后腐蚀
代码几乎相同,只是改动一个参数罢了。
处理结果:
这里写图片描述


形态学梯度

膨胀减去腐蚀
这里写图片描述
又被称为基本梯度。(其他还包括内部梯度、外部梯度、方向梯度)

实例代码:

//基本梯度
void BasicMorphologicalGradient(){
    src = imread("1.png");
    if(!src.data){
        cout << "文件打开失败!" << endl;
        return ;
    }
    namedWindow("原图像",CV_WINDOW_AUTOSIZE);
    imshow("原图像",src);

    //膨胀操作
    Mat kernel = getStructuringElement(MORPH_RECT,Size(11,11),Point(-1,-1));
    dilate(src,dest,kernel);
    namedWindow("膨胀操作",CV_WINDOW_AUTOSIZE);
    imshow("膨胀操作",dest);

    //腐蚀操作
    erode(src,dest,kernel);
    namedWindow("腐蚀操作",CV_WINDOW_AUTOSIZE);
    imshow("腐蚀操作",dest);

    //基本梯度操作
    morphologyEx(src,dest,MORPH_GRADIENT,kernel);
    namedWindow("基本梯度操作",CV_WINDOW_AUTOSIZE);
    imshow("基本梯度操作",dest);

    cvWaitKey();
}

处理结果:
这里写图片描述


顶帽

顶帽是原图像与开操作之间的差值图像。
实例代码:

void TopHat(){
    src = imread("1.png");
    if(!src.data){
        cout << "文件打开失败!" << endl;
        return ;
    }
    namedWindow("原图像",CV_WINDOW_AUTOSIZE);
    imshow("原图像",src);

    //创建结构元素
    Mat kernel = getStructuringElement(MORPH_RECT,Size(7,7),Point(-1,-1));
    //执行开操作
    morphologyEx(src,dest,MORPH_OPEN,kernel);

    namedWindow("开操作后",CV_WINDOW_AUTOSIZE);
    imshow("开操作后",dest);

    //顶帽
    morphologyEx(src,dest,MORPH_TOPHAT,kernel);
    namedWindow("顶帽",CV_WINDOW_AUTOSIZE);
    imshow("顶帽",dest);

    cvWaitKey();
}

处理结果:
这里写图片描述


黑帽

黑帽是闭操作减去原图像

void BlackHat(){
    src = imread("2.png");
    if(!src.data){
        cout << "文件打开失败!" << endl;
        return ;
    }
    namedWindow("原图像",CV_WINDOW_AUTOSIZE);
    imshow("原图像",src);

    //创建结构元素
    Mat kernel = getStructuringElement(MORPH_RECT,Size(7,7),Point(-1,-1));
    //执行开操作
    morphologyEx(src,dest,MORPH_CLOSE,kernel);

    namedWindow("闭操作后",CV_WINDOW_AUTOSIZE);
    imshow("闭操作后",dest);

    //黑帽
    morphologyEx(src,dest,MORPH_BLACKHAT,kernel);
    namedWindow("黑帽",CV_WINDOW_AUTOSIZE);
    imshow("黑帽",dest);

    cvWaitKey();
}

处理结果:
这里写图片描述

  • 8
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值