Skip to content

Commit

Permalink
Harden the trace boundary code
Browse files Browse the repository at this point in the history
A one pixel object could get stuck in an infinite loop in the moore
boundary call.
  • Loading branch information
manthey committed Dec 6, 2024
1 parent d978797 commit 89fe9e8
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 11 deletions.
21 changes: 11 additions & 10 deletions histomicstk/segmentation/label/_trace_object_boundaries_cython.pyx
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,8 @@ def _trace_object_boundaries_cython(long[:, :] im_label not None, long connectiv
# find starting x and y points if not defined
if (x_start == -1) & (y_start == -1):

for i in range(nrows):
for j in range(ncols):
for i in range(1, nrows - 1):
for j in range(1, ncols - 1):

if (im_label[i, j] > 0) & (flag == 0):
# check if the number of points is one
Expand All @@ -41,16 +41,17 @@ def _trace_object_boundaries_cython(long[:, :] im_label not None, long connectiv

bx = []
by = []
if x_start >= 0 and y_start >= 0:

if connectivity == 4:
bx, by = _isbf(
im_label, im_label_90, im_label_180, im_label_270,
x_start, y_start, max_length);
if connectivity == 4:
bx, by = _isbf(
im_label, im_label_90, im_label_180, im_label_270,
x_start, y_start, max_length);

else:
bx, by = _moore(
im_label, im_label_90, im_label_180, im_label_270,
x_start, y_start, max_length);
else:
bx, by = _moore(
im_label, im_label_90, im_label_180, im_label_270,
x_start, y_start, max_length);

return np.asarray(bx), np.asarray(by)

Expand Down
12 changes: 11 additions & 1 deletion tests/test_segmentation_label.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ def test_trace_boundary(self):
[0, 0, 0, 0, 0, 0, 0, 1, 1, 0],
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0]], dtype=bool)

# refenece neighbors for isbf
# reference neighbors for isbf
rx_isbf = [1, 1, 2, 2, 3, 4, 5, 6, 7, 8, 8, 9, 9, 8, 7, 7, 7,
7, 6, 6, 5, 5, 5, 4, 4, 3, 3, 3, 3, 2, 1]
ry_isbf = [7, 8, 8, 7, 6, 6, 6, 6, 6, 7, 8, 8, 7, 7, 6, 5, 4,
Expand All @@ -46,6 +46,16 @@ def test_trace_boundary(self):
np.testing.assert_allclose(rx_moore, x_moore[0])
np.testing.assert_allclose(ry_moore, y_moore[0])

def test_trace_boundary_bad(self):
# Make sure the algorithms terminate work in a degenerate case
m_neighbor = np.array([[0, 0, 0, 0, 0],
[0, 1, 0, 1, 0],
[0, 0, 0, 0, 0]], dtype=bool)
x, y = trace_object_boundaries(m_neighbor, simplify_colinear_spurs=False)
assert not len(x)
x, y = trace_object_boundaries(m_neighbor, 8, simplify_colinear_spurs=False)
assert not len(x)


class TestDeleteBorderLabel:

Expand Down

0 comments on commit 89fe9e8

Please sign in to comment.