Skeleton extraction and watershed algorithm also belong to the morphological processing category, which are placed in the morphology sub-module.
1. Skeleton Extraction
Skeleton extraction, also called binary image refinement. This algorithm can refine a connected area into a pixel width for feature extraction and target topology representation.
The morphology submodule provides two functions for skeleton extraction, namely the skeletonize () function and the Medial_axis () function. Let's look at the Skeletonize () function first.
The format is:skimage.morphology. skeletonize (image)
Both the input and output are a two-value image.
Example 1:
fromSkimageImportMorphology,drawImportNumPy as NPImportMatplotlib.pyplot as Plt#Create a binary image for testingImage = Np.zeros ((400, 400))#generate target object 1 (White U-shape)IMAGE[10:-10, 10:100] = 1image[-100:-10, 10:-10] = 1image[10:-10, -100:-10] = 1#generate target Object 2 (type X)RS, cs = Draw.line (250, 150, 10, 280) forIinchRange (10): Image[rs+ I, cs] = 1RS, CS= Draw.line (10, 150, 250, 280) forIinchRange (20): Image[rs+ I, cs] = 1#generate target Object 3 (O-type)IR, IC =np.indices (image.shape) circle1= (ic-135) **2 + (ir-150) **2 < 30**2Circle2= (ic-135) **2 + (ir-150) **2 < 20**2Image[circle1]= 1Image[circle2]=0#Implementing Skeleton AlgorithmsSkeleton =morphology.skeletonize (image)#Show ResultsFig, (ax1, ax2) = Plt.subplots (Nrows=1, ncols=2, figsize= (8, 4)) ax1.imshow (image, CMap=Plt.cm.gray) Ax1.axis ('off') Ax1.set_title ('Original', fontsize=20) ax2.imshow (skeleton, CMap=Plt.cm.gray) Ax2.axis ('off') Ax2.set_title ('Skeleton', fontsize=20) Fig.tight_layout () plt.show ()
Create a test image with three target objects, respectively, to extract the skeleton, the results are as follows:
Example 2: Skeleton extraction using horse pictures from the system
fromSkimageImportMorphology,data,colorImportMatplotlib.pyplot as Pltimage=Color.rgb2gray (Data.horse ()) Image=1-image#Reversed Phase#Implementing Skeleton AlgorithmsSkeleton =morphology.skeletonize (image)#Show ResultsFig, (ax1, ax2) = Plt.subplots (Nrows=1, ncols=2, figsize= (8, 4)) ax1.imshow (image, CMap=Plt.cm.gray) Ax1.axis ('off') Ax1.set_title ('Original', fontsize=20) ax2.imshow (skeleton, CMap=Plt.cm.gray) Ax2.axis ('off') Ax2.set_title ('Skeleton', fontsize=20) Fig.tight_layout () plt.show ()
Medial_axis is the meaning of the middle axis, the width of the target object is calculated using the Medium axis transformation method (1 value), in the form of:
skimage.morphology. Medial_axis (image, mask=none, return_distance=false)
Mask: Masks. The default is None, and if given a mask, the pixel value within the mask executes the skeleton algorithm.
The Return_distance:bool type value, which defaults to false. If true, the distance transform value is also returned, in addition to the skeleton. The distance here refers to the distance between all the points on the middle axis and the background points.
ImportNumPy as NPImportScipy.ndimage as Ndi fromSkimageImportmorphologyImportMatplotlib.pyplot as Plt#write a function to generate a test imagedefMicrostructure (l=256): N= 5x, y=np.ogrid[0:l, 0:l] Mask=Np.zeros (L, L)) generator= Np.random.RandomState (1) Points= L * Generator.rand (2, n**2) mask[(Points[0]). Astype (Np.int), (points[1]). Astype (np.int)] = 1Mask= Ndi.gaussian_filter (Mask, sigma=l/(4.*N))returnMask >Mask.mean () data= Microstructure (l=64)#generate a test image#calculate the value of the middle axis and distance transformSkel, distance =morphology.medial_axis (data, return_distance=True)#The distance from the point on the middle axis to the background pixelDist_on_skel = distance *Skelfig, (Ax1, AX2)= Plt.subplots (1, 2, figsize= (8, 4)) ax1.imshow (data, CMap=plt.cm.gray, interpolation='Nearest')#display the middle axis with spectral colorAx2.imshow (Dist_on_skel, Cmap=plt.cm.spectral, interpolation='Nearest') Ax2.contour (data, [0.5], colors='W')#Show Contour Linesfig.tight_layout () plt.show ( )
2. Watershed algorithm
The watershed is geographically defined as a ridge in which water usually flows along the sides of the ridge to a different "catchment basin". Watershed algorithm is a classical algorithm for image segmentation, which is based on the topological theory of mathematical morphology segmentation method. If the target objects in the image are linked together, it is more difficult to split up, and the watershed algorithm is often used to deal with such problems, usually with better results.
watershed algorithm can and distance transform combine to find "catchment basin" and "watershed boundary", so that the image can be segmented. The distance transformation of a binary image is the distance from each pixel to the nearest 0-point pixel, and we can use the SCIPY package to calculate the distance transform.
In the following example, you need to separate the two overlapping circles. We first calculate the distance between these white pixels on the circle and the pixels of the black background , select the maximum value in the distance transform as the initial mark point (or the minimum if it is reversed), and the larger of the two basins that begin with these marks, the greater the number of sinks, and the final intersection of the ridges. Disconnected from the ridge, we got two separate circles.
Example 1: Fractal Ridge image Segmentation based on distance transformation
ImportNumPy as NPImportMatplotlib.pyplot as Plt fromSciPyImportNdimage as Ndi fromSkimageImportmorphology,feature#create two images with overlapping circlesX, y = np.indices ((80, 80)) x1, y1, x2, y2= 28, 28, 44, 52R1, R2= 16, 20Mask_circle1= (x-x1) **2 + (y-y1) **2 < r1**2Mask_circle2= (x-x2) **2 + (y-y2) **2 < r2**2Image=np.logical_or (Mask_circle1, Mask_circle2)#now we're separating two circles with a watershed algorithm .Distance = Ndi.distance_transform_edt (image)#Distance TransformLocal_maxi =feature.peak_local_max (distance, Indices=false, Footprint=np.ones (3, 3)), labels=image)#looking for spikesmarkers = Ndi.label (Local_maxi) [0]#Initial marker PointLabels =morphology.watershed (-distance, markers, Mask=image)#a watershed algorithm based on distance transformationFig, axes= Plt.subplots (nrows=2, ncols=2, figsize= (8, 8)) Axes=axes.ravel () ax0, Ax1, ax2, Ax3=axesax0.imshow (image, CMap=plt.cm.gray, interpolation='Nearest') Ax0.set_title ("Original") Ax1.imshow (-distance, Cmap=plt.cm.jet, interpolation='Nearest') Ax1.set_title ("Distance") Ax2.imshow (markers, CMap=plt.cm.spectral, interpolation='Nearest') Ax2.set_title ("Markers") ax3.imshow (labels, cmap=plt.cm.spectral, interpolation='Nearest') Ax3.set_title ("Segmented") forAxinchAxes:ax.axis ('off') Fig.tight_layout () plt.show ()
Watershed algorithms can also be combined with gradients to achieve image segmentation. A general gradient image has a higher pixel value at the edge and a lower pixel value elsewhere, ideally at the edge of the ridge. Therefore, we can find the ridge according to the gradient.
Example 2: Gradient-based watershed image segmentation
ImportMatplotlib.pyplot as Plt fromSciPyImportNdimage as Ndi fromSkimageImportMorphology,color,data,filterimage=Color.rgb2gray (Data.camera ()) denoised= Filter.rank.median (Image, Morphology.disk (2))#Filter Noise#start marker point with gradient values below 10markers = Filter.rank.gradient (denoised, Morphology.disk (5)) <10Markers=Ndi.label (markers) [0]gradient= Filter.rank.gradient (denoised, Morphology.disk (2))#Calculate GradientLabels =morphology.watershed (gradient, markers, mask=image)#gradient-based watershed algorithmFig, axes= Plt.subplots (nrows=2, ncols=2, figsize= (6, 6)) Axes=axes.ravel () ax0, Ax1, ax2, Ax3=axesax0.imshow (image, CMap=plt.cm.gray, interpolation='Nearest') Ax0.set_title ("Original") ax1.imshow (gradient, CMap=plt.cm.spectral, interpolation='Nearest') Ax1.set_title ("Gradient") Ax2.imshow (markers, CMap=plt.cm.spectral, interpolation='Nearest') Ax2.set_title ("Markers") ax3.imshow (labels, cmap=plt.cm.spectral, interpolation='Nearest') Ax3.set_title ("Segmented") forAxinchAxes:ax.axis ('if') Fig.tight_layout () plt.show ()
Python Digital Image Processing (19): Skeleton Extraction and watershed algorithm