Matlab middle filter

I wrote a 3x3 medium filter. It works fine, but it displays the same output image three times instead of one. How to solve a problem?

Code

function [filtr_image] = avgFilter(noisy_image)

    [x,y] = size(noisy_image);
    filtr_image = zeros(x,y);
    for i = 2:x-1
        for j =2:y-1
            sum = 0;
            for k = i-1:i+1
                for l = j-1:j+1
                    sum = sum+noisy_image(k,l);
                end
            end
            filtr_image(i,j) = sum/9.0;
           filtr_image = uint8(filtr_image);

        end
    end

end

      

early

+3


source to share


2 answers


I can't figure out why your code will repeat the image (unless the pattern is caused by an integer overflow: /), but here are some tips:

if you want to use for loops, at least remove the inner loops:

[x,y] = size(noisy_image);
filtr_image = zeros(x,y);
for i = 2:x-1
    for j =2:y-1
        % // you could do this in 1 line if you use mean2(...) instead
        sub = noisy_image(i-1:i+1, j-1:j+1);
        filtr_image = uint8(mean(sub(:))); 
    end
end

      



But do you know about convolution? Matlab has a built-in function for this:

filter = ones(3)/9;
filtr_image = uint8(conv2(noisy_image, filter, 'same'));

      

+1


source


Which is most likely due to the fact that you are supplying the image with a color when the code is specifically for grayscale. Let this be a lesson for you to blindly copy code from source without fully understanding it.

The reason you see "three" is because when you do this to highlight your output filter:

[x,y] = size(noisy_image)

      

If you have a 3D matrix the number of columns reported size

will be y = size(noisy_image,2)*size(noisy_image,3);

. This way, when you iterate over each pixel in your image, in the top column order, each plane will be positioned side by side. What you need to do is either convert the image to grayscale from RGB or filter each plane separately.

In addition, unnecessary casting is performed in the loop. Just do it outside of the loop.

Option number 1 - Filter on a plane

function [filtr_image] = avgFilter(noisy_image)
[x,y,z] = size(noisy_image);
filtr_image = zeros(x,y,z,'uint8');
for a = 1 : z
    for i = 2:x-1
        for j =2:y-1
            sum = 0;
            for k = i-1:i+1
                for l = j-1:j+1
                    sum = sum+noisy_image(k,l,a);
                end
            end
            filtr_image(i,j,a) = sum/9.0;
        end
    end
 end
end

      



Then you would call it by:

filtr_image = avgFilter(noisy_image);

      

Option # 2 - Convert to grayscale

filtr_image = avgFilter(rgb2gray(noisy_image));

      

Minor note

You are using sum

as a variable. This is a very bad choice. sum

is an actual function in MATLAB and you will obscure that function with your variable. This will lead to unintended consequences if you have other functions that rely on sum

for subsequent line-by-line work.

+1


source







All Articles