Thomas Dewitt
Thomas Dewitt

Reputation: 60

Change connection definitions for clear_border in Python

I've been using clear_border from scikit-image and label from scipy to identify areas of adjacent pixels in a 2d array of 1s and 0s. I use clear_border first, which removes all groups of 1 that are touching the edge, and then label the groups that are left with label.

My question is, with label a custom structure parameter can be passed. This determines what is defined to be connected, and in my case it basically allows me to decide whether diagonals are connected. To be concrete, in the array

[[0,0,0,0,0]
 [0,1,0,0,0]
 [0,0,1,1,0]
 [0,0,0,0,0]
 [0,0,0,0,0]

label would find 2 independent objects if [[0,1,0],[1,1,1],[0,1,0]] is used for structure, but only one if [[1,1,1],[1,1,1],[1,1,1]] is used. The problem is, clear_border has no such option and works the same as label when [[1,1,1],[1,1,1],[1,1,1]] is used (in other words, clear_border always defines diagonal pixels to be connected).

So my problem is just that I need to use a function exactly like clear_border, but one that does not define diagonal pixels to be connected. The analogue of passing structure=[[0,1,0],[1,1,1],[0,1,0]] to label.

Update

Based on Juan's answer, here is my general function that I was looking for.

from skimage.segmentation import clear_border
from scipy.ndimage.measurements import label

def clear_border_adjacent(matrix):
    """
        clear_border from skimage.segmentation considers diagonal pixels to be connected, 
        so e.g. all structures will be removed in all of these:
                [[0,0,0,0],                [[0,0,0,0],                [[0,0,0,0], 
                 [0,1,1,0],                 [0,1,1,0],                 [0,1,0,0], 
                 [0,0,0,1],                 [0,0,1,1],                 [1,0,0,0],
                 [0,0,0,0]]                 [0,0,0,0]]                 [0,0,0,0]]
        This function clears the border but only considers adjacent pixels connected, 
        so ex 1 and 3 would still have one structure in output but ex 2 would have 0.
    """
    border_cleared = clear_border(label(matrix)[0])
    border_cleared[border_cleared > 0] = 1
    return border_cleared

Upvotes: 0

Views: 617

Answers (1)

Juan
Juan

Reputation: 5738

I think you can use label first, then clear border, to achieve the same result? If there is a reason why this fails, please make a feature request on https://github.com/scikit-image/scikit-image/issues

Upvotes: 1

Related Questions