1
$\begingroup$

I am computing a spectrogram and I've found a code example online which goes like this:

for jj = 1:size(signal_framewise,2)
    current_frame = signal_framewise(:,jj);
    dtf = fft(current_frame).*gausswin(window_length_s);
    %nfft is half of the fft results (since the fft is symetric)
    out_buffer(:,jj) = dtf(1:nfft); 
end

But I intuitively did it like this:

for jj = 1:size(signal_framewise,2)
    current_frame = signal_framewise(:,jj).*gausswin(window_length_s);
    dtf = fft(current_frame);
    out_buffer(:,jj) = dtf(1:nfft);
end

The difference is, that the guy online applies the window to the finished FFT and I apply it to the signal frame. Question is: What's the right way to do and does it make a difference? I've attached the outputs of the spectrogram and the full code.

[![%% my implementation][1]][1]

clc; clear all; close all;
Fs = 44100;
t_max = 3;
T = 1/Fs;

time = 0:T:(t_max-T);
input = chirp(time,1500,1,8000);

window_length_t = 0.01; %10ms window length
window_length_s = round(0.01 * Fs); %window length in samples
if mod(window_length_s,2) == 0
    window_length_s = window_length_s + 1; %make sure we have odd window size
end

%activate the following for a no overlap implementation
%signal_framewise = buffer(input , window_length_s); 
signal_framewise = buffer(input , window_length_s , floor(window_length_s/2));
nfft =((window_length_s-1)/2)+1;

out_buffer = zeros(nfft,size(signal_framewise,2));
for jj = 1:size(signal_framewise,2)
    current_frame = signal_framewise(:,jj).*gausswin(window_length_s);
    dtf = fft(current_frame);
    out_buffer(:,jj) = dtf(1:nfft);
end

F = linspace(0,Fs/2,nfft);
T = linspace(0,3,size(signal_framewise,2));
surf(T,F,20*log10(abs(out_buffer)), 'EdgeColor', 'none');
axis xy;
axis tight; colormap(jet); view(0, 90);
xlabel('Time');
colorbar;
ylabel('Frequency(Hz)');
set(gca, 'YTickLabel', num2cell(get(gca, 'YTick')));

https://i.stack.imgur.com/abQPZ.jpg

https://i.stack.imgur.com/iMpvW.jpg

$\endgroup$
  • $\begingroup$ I'm not familiar with Matlab so I can't be sure but is it possible that the * operator denotes convolution (when applied in the frequency domain), rather than multiplication? $\endgroup$ – dsp_user Apr 25 '18 at 12:48
  • $\begingroup$ No, ".*" means element-wise multiplication. Convolution is "conv(...)". Element-wise meaning, the first element of the first vector gets multiplied with the first element of the second vector, then the second element of the first vector gets multiplied with the second element of the second vector and so forth $\endgroup$ – Alon Apr 25 '18 at 12:54
  • $\begingroup$ Well, multiplication in the frequency domain corresponds to convolution in the time-domain so perhaps that other guy wanted to do something else (frequency domain filtering is similar to this although he doesn't seem to be using a filter at all, unless we assume the gauss window to be that filter. Anyway, as far as I can tell, the two code snippets are not equivalent. $\endgroup$ – dsp_user Apr 25 '18 at 13:17
0
$\begingroup$

Element-wise multiplication in the spatial/temporal domain with a windowing function serves to reduce the effect of the potentially large jump you get at the signal edge, when making the sampled signal periodic. This jump would otherwise introduce lots of frequencies that might not be present in the signal.

Element-wise multiplication in the frequency domain with a windowing function applies a low-pass filter. Multiplying by a Gaussian window is equivalent to applying a Gaussian filter in the spatial/temporal domain.

If the code you found online were to compute the inverse transform after applying the window, then whoever wrote it would be low-pass filtering. With the code as you posted, I tend to think that person doesn't know what they're doing (or maybe it's just a typo).

$\endgroup$
  • $\begingroup$ de.mathworks.com/matlabcentral/answers/… have a look! It's a very short entry $\endgroup$ – Alon Apr 26 '18 at 8:34
  • $\begingroup$ @JoschKraus it looks like a misplaced parenthesis to me. $\endgroup$ – Cris Luengo Apr 26 '18 at 12:55
  • $\begingroup$ I cant see where there is supposed to be a misplaced parenthesis? $\endgroup$ – Alon Apr 27 '18 at 12:14
  • $\begingroup$ I imagine it could have looked like this: dtf = fft(current_frame.*gausswin(window_length_s));. This just moves the closing parenthesis for fft to the end of the statement. $\endgroup$ – Cris Luengo Apr 27 '18 at 13:19
  • $\begingroup$ Now I understand, thx $\endgroup$ – Alon May 2 '18 at 9:02

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.