基于Opencv实现Matlab的bwmorph中的bridge操作

    xiaoxiao2021-03-26  23

    工程需要,但是不能用matlab,所以用Opencv实现了一下bridge,也不难。

    一. bridge操作的定义

    在官方文档https://cn.mathworks.com/help/images/ref/bwmorph.html中,bridge操作的定义如下: Bridges unconnected pixels, that is, sets 0-valued pixels to 1 if they have two nonzero neighbors that are not connected. For example: 1 0 0 1 0 1 0 0 1 becomes 1 1 0 1 1 1 0 1 1 也就是说,在一个二值化后的图像中,对于任意一个值为0的像素点,如果它周围(4连通或8连通)存在至少2个值为1且属于不同连通区域的像素点,则把这个像素点值修改为1。

    二. 实现思路

    按照定义把所有值为0的像素点都走一遍就ok了,注意每次修改后,需要更新连通区域的信息。

    三. 代码实现

    #include <iostream> #include <opencv2/core/core.hpp> #include <opencv2/highgui/highgui.hpp> #include <opencv2/imgproc/imgproc.hpp> #include <set> using namespace cv; using namespace std; const int dx[] = { 0, 1, 0, -1, 1, -1, 1, -1 }; const int dy[] = { 1, 0, -1, 0, 1, -1, -1, 1 }; set<int> get_neighbors1(Mat src, Mat label_mat, int x, int y, int connectivity = 8) { set<int> neighbors; for (int i = 0; i < connectivity; ++i) { int tmp_x = x + dx[i]; int tmp_y = y + dy[i]; if (tmp_x >= 0 && tmp_x < src.rows && tmp_y >= 0 && tmp_y < src.cols && src.at<uchar>(tmp_x, tmp_y) == 255) { neighbors.insert(label_mat.at<int>(tmp_x, tmp_y)); } } return neighbors; } void bridge(Mat src, Mat &dst, int connectivity = 8) { Mat label_mat; connectedComponents(src, label_mat, connectivity); dst = src.clone(); for (int i = 0; i < src.rows; ++i) { for (int j = 0; j < src.cols; ++j) { uchar pixel = src.at<uchar>(i, j); if (pixel == 0) { if (get_neighbors1(src, label_mat, i, j, 4).size() >= 2) { dst.at<uchar>(i, j) = 255; connectedComponents(dst, label_mat, connectivity); } } } } } int main() { Mat image = imread("C:\\Users\\whai\\Desktop\\1.png"); cvtColor(image, image, COLOR_BGR2GRAY); // Canny(image, image, 100, 200, 3); imshow("修复前", image); waitKey(); Mat dst; bridge(image, dst, 4); imshow("修复后", dst); imwrite("C:\\Users\\whai\\Desktop\\2.png", dst); waitKey(); return 0; }

    四. 效果

    bridge前

    bridge后

    转载请注明原文地址: https://ju.6miu.com/read-658852.html

    最新回复(0)