GraphCuts is the name for a collection of energy minimization algorithms (https://en.wikipedia.org/wiki/Graph_cuts_in_computer_vision). We employ it here for image segmentation.

This scripts performs a marker based image segmentation by constructing a graph from the images voxels and then looking for the globally optimal cut to seperate the marker areas.

Various versions are provided (http://pythonhosted.org/MedPy/graphcut.html), but we will concentrate here on only two.

Gradient based

Original image Foreground (red) and background (green) marker on original image Gradient image

Let's assume we want to segment the ventricle from a brain scan (left image). We first create some (manual or automatic) markers (middle image). We furthermore require a gradient magnitude image of the brain scan, which we can obtain with


In [2]:
medpy_gradient.py resources/b0.nii.gz output/gradient.nii.gz

To execute the graphcut, we call


In [4]:
medpy_graphcut_voxel.py 10 output/gradient.nii.gz resources/b0markers.nii.gz output/graphcut_voxel_gradient.nii.gz --boundary diff_pow

Which results in </td>

Which is acceptable, considering the ad-hoc usage we just performed. The first parameter passed to the script defines the sigma, i.e., the smoothness of the cut. Setting it to high will result in very smooth cuts, lower values allow the graphcut more freedom at the risk of leakages.

Grayvalue based

Another usage of the script does not require the magnitude gradient, but rather the original image. It can be used by calling


In [7]:
medpy_graphcut_voxel.py 1 resources/b0.nii.gz resources/b0markers.nii.gz output/graphcut_voxel_grayvalues.nii.gz --boundary=max_div

Which results in </td>

This result is smoother and dooes better represent the real outline of the ventricles. But it failed to connect one of the foreground markers with the remaining foreground object.

Summary

Graphcuts are a frickle thing. They depend on the quality of the markers and the employed parameters. The examples shown here provide quite acceptable results that could be easily improved with further parameter tuning.

Furthermore, this script only uses the boundary term of graphcut, ignoring the regional term. MedPy does of course support both terms, see the package description for more details: http://pythonhosted.org/MedPy/graphcut.html

For very large (e.g. 4D) images, the voxel based graphcut might be too memory consuming for a standard computer. You might want to consider using the label/region based grapcut shipped with MedPy instead. The label/region version is additionally faster and often produces superior results.


In [ ]: