# How to find the period of a noisy signal using MATLAB's $\tt xcorr$? Here is my code:

function [ T ] = FindPeriodicity2(x,Fs)
ac=xcorr(x,x);
[~,locs]=findpeaks(ac);
T=mean(diff(locs)/Fs);
end


and when I pass the signal x with a Gaussian noise the period is 1.564 but as we know it equals $\pi$, so the answer is about half of the real period in this case. I know I should eliminate some of the peaks found in 'ac', but I have no idea how to choose from peaks such that it works for any signals.The plot of 'ac' is attached . here is the signal x:

Fs=100;
t=0:(1/Fs):30;
n=length(t);
noise=randn(1,n).*0.3;
x=sin(2.*t+pi)+cos(4.*t)+noise;
T=FindPeriodicity2(x,Fs);
disp(T);


any hint would be appreciated.

• "not correct": in what way? What did you expect, what are you getting? Possibly: show some plots! Like this, your answer is too vague to be precisely answered, in my humble opinion. Please edit it! Apr 23, 2017 at 15:50
• Does this question and the answers help? Without more details, as @MarcusMüller suggests, we can't really help much.
– Peter K.
Apr 23, 2017 at 15:55
• I just edited the question. Apr 23, 2017 at 16:44

You are getting that result because you are taking into account other maxima that do not correspond to the points you are actually looking for.

When you call findpeaks() with no other parameter than the input signal, you are taking into account all the points marked with a blue arrow. To determine the period, you just want those inside red circles. Note that, due to the noise, inside some red circles there are more than just one point considered as a peak. That is undesired as well.

You have to put a restriction to find peaks such that they are at least 160 samples away from each other (in this case, due to your signal and its correlation). You can see that if you replace

[~,locs]=findpeaks(ac);

with

[pks,locs] = findpeaks(ac,'MinPeakDistance',300); %Or any number >160

the period will be the expected one.