图像处理——孔洞填充算法

前言:
由于遥感图像通常巨大,opencv自带的imread函数可能读取图像失败,所以用gdal库写个readTif函数;自带的floodfill函数运行会时间太久,所以也自己写叭。。。
先看一下需求:
在这里插入图片描述算法流程:
1、以原图像的补集作为Mask,用来限制膨胀结果;
2、以带有白色边框的黑色图像为初始Marker,用SE对其进行连续膨胀,直至收敛;
3、最后对Marker取补即得到最终图像,与原图相减可得到填充图像。
python代码:

# -*- coding:utf-8 -*-
import numpy as np
import cv2

class kdtc():
    def __init__(self):
        pass

    def readTif(self,fileName):
        import gdal
        dataset = gdal.Open(fileName)
        if dataset == None:
            print(fileName+"文件无法打开")
            return
        im_width = dataset.RasterXSize #栅格矩阵的列数
        im_height = dataset.RasterYSize #栅格矩阵的行数
        im_bands = dataset.RasterCount #波段数
        im_data = dataset.ReadAsArray(0,0,im_width,im_height)#获取数据
        im_geotrans = dataset.GetGeoTransform()#获取仿射矩阵信息
        im_proj = dataset.GetProjection()#获取投影信息
        im_blueBand =  im_data[2,0:im_height,0:im_width]#获取蓝波段
        im_greenBand = im_data[1,0:im_height,0:im_width]#获取绿波段
        im_redBand =   im_data[0,0:im_height,0:im_width]#获取红波段
        #im_nirBand = im_data[3,0:im_height,0:im_width]#获取近红外波段
        im_data = cv2.merge([im_blueBand, im_greenBand, im_redBand])
        #print(type(im_data))
        return im_data

    def kongdongtianchong(self,img_name,TF=True):
        img = self.readTif(img_name)
        img = img[:, :, 0]
        if TF:
            se0 = cv2.getStructuringElement(cv2.MORPH_ELLIPSE, (30, 30))
            img = cv2.dilate(img, se0)
            mask = 255 - img
            
			# 构造Marker
			#marker = np.zeros_like(img)
    		#marker[0, :] = 255
    		#marker[-1, :] = 255
   			#marker[:, 0] = 255
    		#marker[:, -1] = 255
    		#marker_0 = marker.copy()
    		
            # 构造Marker
            SE=cv2.getStructuringElement(cv2.MORPH_ELLIPSE, (50, 50))
            marker=cv2.erode(mask,SE)

            # 形态学重建
            se = cv2.getStructuringElement(shape=cv2.MORPH_CROSS, ksize=(25, 25))
            while True:
                marker_pre = marker
                dilation = cv2.dilate(marker, kernel=se)
                marker = np.min((dilation, mask), axis=0)
                if (marker_pre == marker).all():
                    break
            dst = 255 - marker
            dst=cv2.erode(dst,se0)
            print('----------孔洞填充完成----------')
            return dst
        else:
            return img

猜你喜欢

转载自blog.csdn.net/qq_42823043/article/details/108279767