I have implemented the naive version of non local means without integral images. First image acquisition:
row = 10;
col = 10;
% Patchsize - make sure if code works for different values
patchSize = 4;
% Search window size - make sure if code works for different values
searchWindowSize = 10;
image = imread('r.jpg');
new=imnoise(image,'gaussian');
imshow(new)
ws=floor(searchWindowSize/2);
ps=floor(patchSize/2);
new= padarray(new, [searchWindowSize,searchWindowSize], 'both');
new= padarray(new, [patchSize,patchSize], 'both');
Now, the main non local means function:
unew=zeros(size(new,1),size(new,2));
for i=1+ws+ps:size(new,1)-ws-ps
for j=1+ws+ps:size(new,2)-ws-ps
sear=new(i-ws:i+ws,j-ws:j+ws);
%imshow(new(i-ws:i+ws,j-ws:j+ws))
sear=padarray(sear,[ps,ps],'both');
patch=new(i-ps:i+ps,j-ps:j+ps);
dis=[];
ind=1;
sums=0;
for ii=1+ps:size(sear,1)-ps
for jj=1+ps:size(sear,1)-ps
patchn=new(ii-ps:ii+ps,jj-ps:jj+ps);
ssd=(patchn-patch).*2;
psum=0;
for mj=1:patchSize
for gj=1:patchSize
psum= psum+ssd(mj,gj);
end
end
dis(ind)=psum;
sums=sums+exp(-max(dis(ind)*dis(ind)-2*0.1*0.1,0)/0.75*0.75);
ind=ind+1;
end
end
new(i,j)=sums;
end
end
My initial image:
My final image:
There are many issues with the code. Here is a non-exhaustive list:
You don’t do anything with color, it looks like your code is written for a grey-value image. But you put a color image through it. Consequently, only the red channel is modified.
You write into the same image you read from. You cannot do this, as you’re using a combination of input and output pixels to generate the next output pixel. Instead, read from one image, write to another one.
A weighted mean is computed by summing value*weight
, and then dividing by the sum of the weights at the end. You don’t do this division.
You crop your search area from your image, then pad it. This makes no sense. You should crop a larger region from your image.
You keep an array dis
, you write to it, but you don’t make use of it. That is, you write a new element, then only read this new element; you never go back and look at the older values. Why does this array exist?
Your inner two loops can be written as psum = sum(ssd(:))
.
ssd
is twice the difference. You probably want to look at the square difference, or the absolute difference.