4.2. Deriving an interpolation-based ring removal method

The methods presented in section 3 mainly use smoothing filters to remove stripe artifacts. This certainly affects neighboring pixels resulting in side-effect artifacts. Here, the author derives an method where stripe artifacts are removed by interpolation with neighbors. The method is a combination of algorithm 4, 5, and 6 in Ref. [1].

Code

sarepy.prep.stripe_removal_improved.remove_stripe_based_interpolation(sinogram, snr, size, drop_ratio=0.1, norm=True)[source]

Combination of algorithm 4, 5, and 6 in Ref. [1]. Remove stripes using a detection technique and an interpolation method. Angular direction is along the axis 0.

Parameters
  • sinogram (array_like) – 2D array. Sinogram image

  • snr (float) – Ratio used to segment between useful information and noise.

  • size (int) – Window size of the median filter used to detect stripes.

  • drop_ratio (float, optional) – Ratio of pixels to be dropped, which is used to to reduce the possibility of the false detection of stripes.

  • norm (bool, optional) – Apply normalization if True.

Returns

ndarray – 2D array. Stripe-removed sinogram.

References

1

https://doi.org/10.1364/OE.26.028396

How it works

It works like the method of removing large stripes. However, in step 3 the selective correction is replaced by interpolation, the same as used in the method of removing unresponsive and fluctuating stripes.

Demonstration

  • Remove small-to-medium stripes:

    import numpy as np
    import sarepy.losa.loadersaver as losa
    import sarepy.prep.autocentering as cen
    import sarepy.reco.reconstruction as rec
    from sarepy.prep.stripe_removal_improved import remove_stripe_based_interpolation
    
    sinogram = losa.load_image("../data/sinogram_normal.tif")
    (nrow, ncol) = sinogram.shape
    center = cen.find_center_vo(sinogram, ncol // 2 - 30, ncol // 2 + 30, step_cor=0.5)
    ratio = (min(center, abs(ncol - center))) / (ncol * 0.5)
    rec_image = rec.recon_gridrec(-np.log(sinogram), center, ratio=ratio)
    losa.save_image("../data/output/rec1_before.tif", rec_image)
    sinogram = remove_stripe_based_interpolation(sinogram, 3.0, 31)
    rec_image = rec.recon_gridrec(-np.log(sinogram), center, ratio=ratio)
    losa.save_image("../data/output/rec1_after.tif", rec_image)
    
    ../../_images/fig110.jpg

    Figure 1. Reconstructed images before (a) and after (b) removing stripe artifacts.

  • Remove large stripes:

    sinogram = losa.load_image("../data/sinogram_large_stripe.tif")
    (nrow, ncol) = sinogram.shape
    center = cen.find_center_vo(sinogram, ncol // 2 - 30, ncol // 2 + 30, step_cor=0.5)
    ratio = (min(center, abs(ncol - center))) / (ncol * 0.5)
    rec_image = rec.recon_gridrec(-np.log(sinogram), center, ratio=ratio)
    losa.save_image("../data/output/rec2_before.tif", rec_image)
    sinogram = remove_stripe_based_interpolation(sinogram, 3.0, 51)
    rec_image = rec.recon_gridrec(-np.log(sinogram), center, ratio=ratio)
    losa.save_image("../data/output/rec2_after.tif", rec_image)
    
    ../../_images/fig28.jpg

    Figure 2. Reconstructed images before (a) and after (b) removing stripe artifacts.

  • Remove dead stripes:

    sinogram = losa.load_image("../data/sinogram_dead_stripe.tif")
    (nrow, ncol) = sinogram.shape
    center = cen.find_center_vo(sinogram, ncol // 2 - 30, ncol // 2 + 30, step_cor=0.5)
    ratio = (min(center, abs(ncol - center))) / (ncol * 0.5)
    rec_image = rec.recon_gridrec(-np.log(sinogram), center, ratio=ratio)
    losa.save_image("../data/output/rec3_before.tif", rec_image)
    sinogram = remove_stripe_based_interpolation(sinogram, 3.0, 51)
    rec_image = rec.recon_gridrec(-np.log(sinogram), center, ratio=ratio)
    losa.save_image("../data/output/rec3_after.tif", rec_image)
    
    ../../_images/fig36.jpg

    Figure 3. Reconstructed images before (a) and after (b) removing stripe artifacts.