Convolution in frequency domain matlab - matlab

I just stumbled upon this question and am trying to know about its effects by practically testing it.
Consider a (nxn) Gaussian kernel. Choose the appropriate variance for
the same. Perform linear and circular convolution in the frequency
domain with this kernel on an image. Can you say anything about the
results?
I tried to implement the above in Matlab , with the following code.
clc;
close all;
clear all;
I = imread('my_face.jpg');
Irez = imresize(I,[512 512]); %resize image
figure(1);
imshow(Irez);
Irez = rgb2gray(Irez);
M = 2*size(I,1)+1;
N = 2*size(I,2)+1;
Ifreq = fft2(I,M,N);
gaus = fspecial('gaussian',5,0.7);
Igaus = conv2(gaus,abs(Ifreq));
Iface = real(ifft2(Igaus));
Iout = Iface(1:size(I,1),1:size(I,2));
figure(2)
imshow(Iout);
My questions are :
Am I on the right track? Am I doing what the problem is expecting me to? Or should I take or consider the fft of the gaussian kernel or have a similar Gaussian kernel in frequency domain? Please do tell me if you guys found the right way to achieve this.
Linear convolution's equivalent is multiplication. What is the equivalent of circular convolution?
Moreover, the above code is giving me the following error :
Undefined function or method 'conv2' for input arguments of type
'double' and attributes 'full 3d real'
It is obvious that both have to be double for input of conv2. Can you please help me to practically implement the problem?

I seems that you are providing right arguments in fspecial function. You have to specify the number of columns and rows in this function. I copied the below lines from matlab help:
h = fspecial('average', hsize) returns an averaging filter h of size hsize. The argument hsize can be a vector specifying the number of rows and columns in h, or it can be a scalar, in which case h is a square matrix. The default value for hsize is [3 3].
gaus = fspecial('gaussian', [M N],5,0.7);
You can find more about it here: http://www.mathworks.se/help/images/ref/fspecial.html

Related

Matlab quadratic equation/convolution

I've got a convolution where the final result is
y=(-t/2)+5t=6
Is there any chance to check this in matlab but not through convolution, I have programmed that part. What I am wondering is it possible to plot the signal using this equation and compare it with the one that I got with coding convolution.
You can plot functions easily in matlab: look at the examles from here.
For example using this code:
t = 0:.1:10
plot(t,(-t/2)+5*t)
will plot you your function between the values x = [0, 10].

Matlab. Poisson fit. Factorial

I have a histogram that seems to fit a poisson distribution.
In order to fit it, I declare the function myself as follows
xdata; ydata; % Arrays in which I have stored the data.
%Ydata tell us how many times the xdata is repeated in the set.
fun= #(x,xdata) (exp(-x(1))*(x(1).^(xdata)) )/(factorial(xdata)) %Function I
% want to use in the fit. It is a poisson distribution.
x0=[1]; %Approximated value of the parameter lambda to help the fit
p=lsqcurvefit(fun,x0,xdata,ydata); % Fit in the least square sense
I find an error. It probably has to do with the "factorial". Any ideas?
Factorial outputs a vector from vector xdata. Why are you using .xdata in factorial?
For example:
data = [1 2 3];
factorial(data) is then [1! 2! 3!].
Try ./factorial(xdata) (I cannot recall if the dot is even necessary at this case.)
You need to use gamma(xdata+1) function instead of factorial(xdata) function. Gamma function is a generalized form of factorial function which can be used for real and complex numbers. Thus, your code would be:
fun = #(x,xdata) exp(-x(1))*x(1).^xdata./gamma(xdata+1);
x = lsqcurvefit(fun,1,xdata,ydata);
Alternatively, you can MATLAB fitdist function which is already optimized and you might get better results:
pd = fitdist(xdata,'Poisson','Frequency',ydata);
pd.lambda

Fitting a 2D Gaussian to 2D Data Matlab

I have a vector of x and y coordinates drawn from two separate unknown Gaussian distributions. I would like to fit these points to a three dimensional Gauss function and evaluate this function at any x and y.
So far the only manner I've found of doing this is using a Gaussian Mixture model with a maximum of 1 component (see code below) and going into the handle of ezcontour to take the X, Y, and Z data out.
The problems with this method is firstly that its a very ugly roundabout manner of getting this done and secondly the ezcontour command only gives me a grid of 60x60 but I need a much higher resolution.
Does anyone know a more elegant and useful method that will allow me to find the underlying Gauss function and extract its value at any x and y?
Code:
GaussDistribution = fitgmdist([varX varY],1); %Not exactly the intention of fitgmdist, but it gets the job done.
h = ezcontour(#(x,y)pdf(GaussDistributions,[x y]),[-500 -400], [-40 40]);
Gaussian Distribution in general form is like this:
I am not allowed to upload picture but the Formula of gaussian is:
1/((2*pi)^(D/2)*sqrt(det(Sigma)))*exp(-1/2*(x-Mu)*Sigma^-1*(x-Mu)');
where D is the data dimension (for you is 2);
Sigma is covariance matrix;
and Mu is mean of each data vector.
here is an example. In this example a guassian is fitted into two vectors of randomly generated samples from normal distributions with parameters N1(4,7) and N2(-2,4):
Data = [random('norm',4,7,30,1),random('norm',-2,4,30,1)];
X = -25:.2:25;
Y = -25:.2:25;
D = length(Data(1,:));
Mu = mean(Data);
Sigma = cov(Data);
P_Gaussian = zeros(length(X),length(Y));
for i=1:length(X)
for j=1:length(Y)
x = [X(i),Y(j)];
P_Gaussian(i,j) = 1/((2*pi)^(D/2)*sqrt(det(Sigma)))...
*exp(-1/2*(x-Mu)*Sigma^-1*(x-Mu)');
end
end
mesh(P_Gaussian)
run the code in matlab. For the sake of clarity I wrote the code like this it can be written more more efficient from programming point of view.

Using matlab to fit data with negative binomial distribution under given p?

How to use matlab to fit data with negative binomial distribution under given p?
Looks like a job for mle in the statistics toolbox. You'll need to express the negative binomial distribution (or the log of it, which will probably be easier) as a function of p and whatever else, and invent some starting parameters to hand in.
If you mean fit as a function of the other parameter R with P fixed, the following shows how to use mle to fix the value of one parameter and estimate the other:
x = nbinrnd(20,.5,1000,1);
params = nbinfit(x) % unconstrained fit
r = mle(x,'pdf',#(x,r)nbinpdf(x,r,.5),'start',23) % constrain P=0.5
% Plot log likelihood as a function of R
rr = linspace(15,25);
yy = zeros(size(rr));
for j=1:length(rr)
yy(j) = sum(log(nbinpdf(x,rr(j),.5)));
end
plot(rr,yy,'-',...
params(1),sum(log(nbinpdf(x,params(1),params(2)))),'o')
legend(sprintf('r=%f,p=.5',r), sprintf('r=%f,p=%f',params),'location','sw')

Mean filter for smoothing images in Matlab

I need to test some basic image processing techniques in Matlab. I need to test and compare especially two types of filters: mean filter and median filter.
To smooth image using median filtering, there is a great function medfilt2 from image processing toolbox. Is there any similar function for mean filter? Or how to use the filter2 function to create the mean filter?
One of the most important things for me is to have the possibility of setting radius of the filter. I.e. for median filter, if I want the [3 x 3] radius (mask), I just use
imSmoothed = medfilt2(img, [3 3]);
I would like to achieve something similar for mean filter.
h = fspecial('average', n);
filter2(h, img);
See doc fspecial:
h = fspecial('average', n) returns an averaging filter. n is a 1-by-2 vector specifying the number of rows and columns in h.
I see good answers have already been given, but I thought it might be nice to just give a way to perform mean filtering in MATLAB using no special functions or toolboxes. This is also very good for understanding exactly how the process works as you are required to explicitly set the convolution kernel. The mean filter kernel is fortunately very easy:
I = imread(...)
kernel = ones(3, 3) / 9; % 3x3 mean kernel
J = conv2(I, kernel, 'same'); % Convolve keeping size of I
Note that for colour images you would have to apply this to each of the channels in the image.
I = imread('peppers.png');
H = fspecial('average', [5 5]);
I = imfilter(I, H);
imshow(I)
Note that filters can be applied to intensity images (2D matrices) using filter2, while on multi-dimensional images (RGB images or 3D matrices) imfilter is used.
Also on Intel processors, imfilter can use the Intel Integrated Performance Primitives (IPP) library to accelerate execution.
and the convolution is defined through a multiplication in transform domain:
conv2(x,y) = fftshift(ifft2(fft2(x).*fft2(y)))
if one channel is considered... for more channels this has to be done every channel
f=imread(...);
h=fspecial('average', [3 3]);
g= imfilter(f, h);
imshow(g);