Search code examples
imagematlabimage-processingedge-detection

Best method to find edge of noise image


I have a noise image I such as the bellow figure. Assume that it is Gaussian noise. Currently, I am using two steps to find the edge

  1. Smooth the image using Gaussian filter G
  2. Find edge based on the equation

    g=1/(1+β∇ (I*G)^2)

where G is gaussian filter. β is weight to control the noise level.

However, the Gaussian filter is reason for losing of edge in image. I want to find a better method that can preserve edge information. Could you suggest to me the best method to find the edge of that image?

This is my result for above steps

enter image description here

Here's the image I am working on with the noise added:

enter image description here

To get the edges, this is the MATLAB code I wrote:

beta=0.01;
G = fspecial('gaussian',[3 3],1);
I_G = conv2(I,G,'same');
[Gx,Gy] = gradient(I_G);
NormGrad = sqrt(Gx.^2 + Gy.^2); 
g = 1./ (1 + beta* NormGrad.^2);
imshow(g,[]);

Solution

  • Canonical edge-preserving smoothing filters should be quite adequate for your particular application. These simultaneously remove noise (Gaussian distributed I should add...) while maintaining edges as best as possible. Classic examples include the bilateral filter, the Guided image filter by Kaiming He, Domain Transform filtering by Gastal and Oliveira (which I have successfully used in the past) and even anisotropic diffusion.

    To try something quickly, the Guided image filter is now included as an official function that's part of the image processing toolbox since MATLAB R2014a via the imguidedfilter function. If you don't have MATLAB R2014a or up, then you can download the raw MATLAB source of the code via this link here: http://kaiminghe.com/eccv10/guided-filter-code-v1.rar, but you can get this from the main website I linked to you above.

    Assuming you don't have R2014a, download the Guided image filter code and let's use it to filter your example. Given your link to the example image that was corrupted with noise, I downloaded it and am using it in the code below:

    I = im2double(imread('https://i.sstatic.net/ACRE8.png')); %// Load in sample image that was corrupted by noise
    r = 2; %// Parameters for the Guided image filter
    eps = 0.1^2;
    
    %// Filter the image, using itself as a guide
    q = guidedfilter(I, I, r, eps);
    
    %// Show the original image and the filtered result
    figure;
    subplot(1,2,1); imshow(I, []);
    subplot(1,2,2); imshow(q, []);
    

    We show the original image, then the guided filter result on the right:

    enter image description here

    Once we have that, try using any canonical edge detector to detect the edges. The one you're using pre-blurs the image before finding the edges, but that uses standard smoothing and it will miss out on some edges. Because using the Guided image filter brings us to a point where the edges are maintained and the overall image is essentially noise free, we can try something simple like a Sobel filter on the edge smoothed result:

    [Gmag,~] = imgradient(q, 'sobel');
    imshow(max(Gmag(:)) - Gmag,[]);
    

    The above code uses imgradient to find image gradients and then we show the image by inverting the intensities so that the black values become white and white become black as seen in your example.

    ... and we get this:

    enter image description here

    As you can see, even with the presence of noise, we still were able to hammer out a lot of the edges.