Segmenting overlapping/ touching nuclei with scikit_image

Hi,
Many thanks in advance, to all who respond,
I want to use python and scikit_image to segment the overlapping nuclei shown in the ‘dilate’ image, it is thresholded and dilated from the original.
I tried it many different ways using watershed but could not manage,

what I aim to do in the end is get a band area around nucleus and use it as a mask.
I take nuclei image, threshold, dilate and get that band by subtracting the two, but at the point of dilation the borders of some nuclei start touching and I want to be able to separate those.

I will really appreciate if I can get some help from the scikit group
@jni , @jkh1

thresh dilate bands

code:

import numpy as np
from matplotlib import pyplot as plt
import pandas as pd
import cv2
from cv2 import dilate, erode
from skimage.util import img_as_ubyte, img_as_float
import os
import sys
from skimage import morphology
from skimage import io
from skimage import segmentation
from skimage import feature
from skimage.feature import peak_local_max
from skimage.morphology import watershed
from skimage.segmentation import mark_boundaries, flood, flood_fill
from skimage.measure import regionprops, label, regionprops_table
from scipy import ndimage as ndi
from skimage.morphology import remove_small_objects, binary_erosion, binary_dilation, remove_small_holes, dilation
from skimage.segmentation import clear_border, watershed
from skimage.filters import  threshold_otsu, threshold_triangle, gaussian, threshold_local


img = io.imread('img')
img = img.astype(np.uint8)
blur = ndi.gaussian_filter(img, 3)
thresh = threshold_otsu(blur)
binary = img> thresh
filled = ndi.binary_fill_holes(binary) 
filled = img_as_ubyte(filled)
kernel=np.ones((3,3), np.uint8)

dilated = cv2.dilate(filled, kernel, iterations=50)
rim = dilated-filled

Hi,
You will need to label all your objects to be able to distinguish them. You can use skimage.measure.label for that. Then you can use a very recent function to expand your labels and avoid merging them: skimage.segmentation.expand_labels. This example in the scikit-image docs does more or less what you need so you can take inspiration from it: Expand segmentation labels without overlap — skimage v0.19.0.dev0 docs

Guillaume

5 Likes

Hi,
Thank you so much for your swift reply. Yes it worked very well this way, I wanted to be able to keep a thicker rim (I had to roll back the distance in expand_labels from 50 to 25) but will have to settle for this for now,
Many thanks again,