如何解决分水岭分割:无法拆分某些单元格
我试图分割细胞核的图像,但最终结果分割不足。似乎出现了一些大斑点,最好将其分解为较小的对象,例如右边缘的对象,请参见下文。
请问有什么我可以做的。我想使用分水岭分割(skimage
或opencv
)来分割这些大单元,例如右边缘中间的蓝色单元。
到目前为止,我的代码如下:
def segment_dapi(img_in):
img = cv2.cvtColor(img_in,cv2.COLOR_BGR2GRAY)
kernel = np.ones((3,3),np.uint8)
# set the parameters
thresh = 90
min_size = 5
# Adjust brightness
lims = stretchlim(img)
img_adj = imadjust(img,lims)
# Threshold the image
thres_val = np.percentile(img,thresh)
_,bw_img = cv2.threshold(img_adj,thres_val,255,cv2.THRESH_BINARY)
# Apply morphology opening to remove small objects
img_obj = cv2.morphologyEx(bw_img,cv2.MORPH_OPEN,kernel,iterations=1)
bg = cv2.dilate(img_obj,iterations=1) # black points belong to the background
# white points (value = 255) belong to the foreground
dist_transform = cv2.distanceTransform(img_obj,cv2.DIST_L2,3)
_,fg = cv2.threshold(dist_transform,min_size,cv2.THRESH_BINARY)
fg = np.uint8(fg)
fg_temp = 255/fg.max() * fg
x = cv2.subtract(bg,fg)
_,markers = cv2.connectedComponents(fg)
markers = markers + 1 # prevent the markers from having values = 0
markers[x == 255] = 0
'''
markers:
> 1: absolute foreground
= 1: absolute background
= 0: unknown area (TBD by watershed)
'''
markers = cv2.watershed(img_in,markers)
img_in[markers == -1] = [0,255]
cv2.imwrite('watershed_borders.tif',img_in);
small_img = cv2.resize(img_in,None,fx=1/2,fy=1/2)
# cv2.imshow('Overlay',small_img)
# cv2.waitKey(0)
'''
markers after watershed:
= 0: background (set by watershed)
= 1: background (because the markers have been shifted by 1)
> 1: object labels
- 1: borders between object
'''
markers[markers>0] = markers[markers>0]-1
markers[markers == -1] = 0
print(markers.max())
overlay = color.label2rgb(markers,bg_label=0)
my_dpi = 72
fig,ax = plt.subplots(figsize=(6000 / my_dpi,6000 / my_dpi),dpi=my_dpi)
plt.imshow(overlay)
ax.set_axis_off()
plt.tight_layout()
plt.show()
def stretchlim(img):
nbins = 255
tol_low = 0.01
tol_high = 0.99
sz = np.shape(img)
if len(sz) == 2:
img = img[:,:,None]
sz = np.shape(img)
p = sz[2]
ilowhigh = np.zeros([2,p])
for i in range(0,p):
hist,bins = np.histogram(img[:,i].ravel(),nbins+1,[0,nbins])
cdf = np.cumsum(hist) / sum(hist)
ilow = np.argmax(cdf > tol_low)
ihigh = np.argmax(cdf >= tol_high)
if ilow == ihigh:
ilowhigh[:,i] = np.array([1,nbins])
else:
ilowhigh[:,i] = np.array([ilow,ihigh])
lims = ilowhigh / nbins
return lims
def imadjust(img,lims):
lims = lims.flatten()
lowIn = lims[0]
highIn = lims[1]
lowOut = 0
highOut = 1
gamma = 1
lut = adjustWithLUT(img,lowIn,highIn,lowOut,highOut,gamma)
out = lut[img].astype(np.uint8)
return out
def adjustWithLUT(img,gamma):
lutLength = 256 # assumes uint8
lut = np.linspace(0,1,lutLength)
lut = adjustArray(lut,gamma)
lut = img_as_ubyte(lut)
return lut
def adjustArray(img,lIn,hIn,lOut,hOut,g):
# %make sure img is in the range [lIn;hIn]
img = np.maximum(lIn,np.minimum(hIn,img))
out = ((img - lIn) / (hIn - lIn)) ** g
out = out ** (hOut - lOut) + lOut
return out
解决方法
您可能需要花费很长时间才能找到准确的参数来很好地进行分割,但是根据我的经验,它有些挑剔,因此对于要分割的下一张图片不起作用。这些天,我实际上会建议您使用经过训练的深度学习网络,例如cellpose。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。