Escenario: Comparación de diferentes implementaciones del mismo algoritmo de umbralización#
En este cuaderno compararemos diferentes implementaciones del mismo algoritmo. Como ejemplo, seleccionamos el método de Otsu para umbralización binaria en combinación con etiquetado de componentes conectados. El algoritmo fue publicado hace más de 40 años y uno podría suponer que todas las implementaciones comunes de este algoritmo muestran resultados idénticos.
Ver también#
from skimage.io import imread, imshow, imsave
from skimage.filters import threshold_otsu
from skimage.measure import label
from skimage.color import label2rgb
Implementación 1: ImageJ#
Como primera implementación, echamos un vistazo a ImageJ. Lo usaremos como parte de la distribución Fiji. El siguiente código de Macro de ImageJ abre “blobs.tif”, lo umbraliza usando el método de Otsu y aplica el etiquetado de componentes conectados. La imagen de etiquetas resultante se guarda en el disco. Puedes ejecutar este script en el editor de scripts de Fiji haciendo clic en File > New > Script.
Nota: Al ejecutar este script, debes adaptar la ruta de los datos de imagen para que se ejecute en tu computadora.
with open('blobs_segmentation_imagej.ijm') as f:
print(f.read())
open("C:/structure/code/clesperanto_SIMposium/blobs.tif");
// binarization
setAutoThreshold("Otsu dark");
setOption("BlackBackground", true);
run("Convert to Mask");
// Connected component labeling + measurement
run("Analyze Particles...", " show=[Count Masks] ");
// Result visualization
run("glasbey on dark");
// Save results
saveAs("Tiff", "C:/structure/code/clesperanto_SIMposium/blobs_labels_imagej.tif");
El resultado se ve entonces así:
imagej_label_image = imread("blobs_labels_imagej.tif")
visualization = label2rgb(imagej_label_image, bg_label=0)
imshow(visualization)
<matplotlib.image.AxesImage at 0x1d290a79520>
Implementación 2: scikit-image#
Como segunda implementación usaremos scikit-image. Como se puede usar desde cuadernos jupyter, también podemos volver a examinar de cerca el flujo de trabajo.
Comenzamos cargando y visualizando la imagen cruda de blobs.
blobs_image = imread("blobs.tif")
imshow(blobs_image, cmap="Greys_r")
C:\Users\rober\miniconda3\envs\bio_39\lib\site-packages\skimage\io\_plugins\matplotlib_plugin.py:150: UserWarning: Float image out of standard range; displaying image with stretched contrast.
lo, hi, cmap = _get_display_range(image)
<matplotlib.image.AxesImage at 0x1d290cfd7c0>
El método threshold_otsu se usa entonces para binarizar la imagen.
# determinar umbral
threshold = threshold_otsu(blobs_image)
# aplicar umbral
binary_image = blobs_image > threshold
imshow(binary_image)
<matplotlib.image.AxesImage at 0x1d290f67280>
Para el etiquetado de componentes conectados, usamos el método label. La visualización de la imagen de etiquetas se produce usando el método label2rgb.
# etiquetado de componentes conectados
skimage_label_image = label(binary_image)
# visualizarlo en colores
visualization = label2rgb(skimage_label_image, bg_label=0)
imshow(visualization)
<matplotlib.image.AxesImage at 0x1d290d2f940>
Para comparar las imágenes más tarde, también guardamos esta en el disco.
imsave("blobs_labels_skimage.tif", skimage_label_image)
C:\Users\rober\AppData\Local\Temp\ipykernel_6744\179771585.py:1: UserWarning: blobs_labels_skimage.tif is a low contrast image
imsave("blobs_labels_skimage.tif", skimage_label_image)
Implementación 3: clesperanto / python#
La tercera implementación del mismo flujo de trabajo también se ejecuta desde python y utiliza pyclesperanto.
Nota: Al ejecutar este script, debes adaptar la ruta de los datos de imagen para que se ejecute en tu computadora.
import pyclesperanto_prototype as cle
blobs_image = cle.imread("C:/structure/code/clesperanto_SIMposium/blobs.tif")
cle.imshow(blobs_image, "Blobs", False, 0, 255)
# Umbral Otsu
binary_image = cle.create_like(blobs_image)
cle.threshold_otsu(blobs_image, binary_image)
cle.imshow(binary_image, "Umbral Otsu de la Imagen CLIJ2 de blobs.gif", False, 0.0, 1.0)
# Etiquetado de Componentes Conectados Box
label_image = cle.create_like(binary_image)
cle.connected_components_labeling_box(binary_image, label_image)
cle.imshow(label_image, "Etiquetado de Componentes Conectados Box del Umbral Otsu de la Imagen CLIJ2 de blobs.gif", True, 0.0, 64.0)
También guardaremos esta imagen para una comparación posterior.
imsave("blobs_labels_clesperanto_python.tif", label_image)
Implementación 4: clesperanto / Jython#
La cuarta implementación utiliza clesperanto dentro de Fiji. Para hacer que este script se ejecute en Fiji, por favor activa los sitios de actualización clij, clij2 y clijx-assistant en tu Fiji. Puedes notar que este script es idéntico al anterior. Solo el guardado del resultado funciona de manera diferente.
Nota: Al ejecutar este script, debes adaptar la ruta de los datos de imagen para que se ejecute en tu computadora.
with open('blobs_segmentation_clesperanto.py') as f:
print(f.read())
# To make this script run in Fiji, please activate the clij, clij2
# and clijx-assistant update sites in your Fiji.
# Read more:
# https://clij.github.io/
#
# To make this script run in python, install pyclesperanto_prototype:
# conda install -c conda-forge pyopencl
# pip install pyclesperanto_prototype
# Read more:
# https://clesperanto.net
#
import pyclesperanto_prototype as cle
blobs_image = cle.imread("C:/structure/code/clesperanto_SIMposium/blobs.tif")
cle.imshow(blobs_image, "Blobs", False, 0, 255)
# Threshold Otsu
binary_image = cle.create_like(blobs_image)
cle.threshold_otsu(blobs_image, binary_image)
cle.imshow(binary_image, "Threshold Otsu of CLIJ2 Image of blobs.gif", False, 0.0, 1.0)
# Connected Components Labeling Box
label_image = cle.create_like(binary_image)
cle.connected_components_labeling_box(binary_image, label_image)
cle.imshow(label_image, "Connected Components Labeling Box of Threshold Otsu of CLIJ2 Image of blobs.gif", True, 0.0, 64.0)
# The following code is ImageJ specific. If you run this code from
# Python, consider replacing this part with skimage.io.imsave
from ij import IJ
IJ.saveAs("tif","C:/structure/code/clesperanto_SIMposium/blobs_labels_clesperanto_imagej.tif");
También echaremos un vistazo al resultado de este flujo de trabajo:
imagej_label_image = imread("blobs_labels_clesperanto_imagej.tif")
visualization = label2rgb(imagej_label_image, bg_label=0)
imshow(visualization)
<matplotlib.image.AxesImage at 0x1d291513a90>