3
votes

I'm making a bandpass filter and I've created a signal with some unwanted frequencies based on sinusoids:

Fs = 8e3; % Sampling Rate
fn = Fs/2; % Nyquist frequency
L = 1e3;  % Length of signal 
T = 1/Fs; % Sampling period
t = T*linspace(0,L,Fs); % Time domain

% Frequencies in Hz
f1 = 1500;
f2 = 700;
f3 = 2500;
f4 = 3500;

% Signal
x = 6*sin(2*pi*f1*t);

% Noise
noise = 3*sin(2*pi*f2*t)...
      + 2*sin(2*pi*f3*t)...
      + 1*sin(2*pi*f4*t);

x_noise = x + noise;

I then create a Butterworth bandpass filter:

[b,a] = butter(10,[1000 2000]/fn,'bandpass');

The signal in time and frequency space, with the bandpass response (with freqz) looks like this:

Fig. 1 Signal with corruption | Fig. 2 Frequency with bandpass response

I would've figured from here on, simply doing

xf = filter(b,a,x_noise);

would've yielded something very similar to the original signal, but alas, what I get is really far from the filtered signal with a high response far from the bandpass.

What am I doing wrong here?

Here's the full code:

clear all
Fs = 8e3; % Sampling Rate
fn = Fs/2; % Nyquist frequency
L = 1e3;  % Length of signal 
T = 1/Fs; % Sampling period
t = T*linspace(0,L,Fs); % Time domain

% Frequencies in Hz
f1 = 1500;
f2 = 700;
f3 = 2500;
f4 = 3500;

% Signal
x = 6*sin(2*pi*f1*t);

% Noise
noise = 3*sin(2*pi*f2*t)...
      + 2*sin(2*pi*f3*t)...
      + 1*sin(2*pi*f4*t);

x_noise = x + noise;

subplot(221); 
idx = 1:round(length(t)/30);
plot(t(idx),x(idx),t(idx),x_noise(idx));
xlabel('Time (s)'); ylabel('Signal Amplitudes');
legend('Original signal','Noisy signal');

% Frequency space
f = fn*linspace(0,1,L/2+1);
X = fft(x_noise)/L;

[b,a] = butter(10,[1000 2000]/fn,'bandpass');
h = abs(freqz(b,a,floor(L/2+1)));

subplot(222);
plot(f,abs(X(1:L/2+1)),f,h*max(abs(X)));
xlabel('Freq (Hz)'); ylabel('Frequency amplitudes');
legend('Fourier Transform of signal','Filter amplitude response');

% Filtered signal
xf = filter(b,a,x_noise);
subplot(223)
plot(t(idx),xf(idx));
xlabel('Time (s)'); ylabel('Signal Amplitudes');
legend('Filtered signal');

% Filtered in frequency space
Xf = abs(fft(xf)/L);
subplot(224);
plot(f,Xf(1:L/2+1),f,h*5e-6);
xlabel('Freq (Hz)'); ylabel('Frequency amplitudes');
legend('Fourier Transform of filtered signal','Bandpass');
1

1 Answers

1
votes

Your time variable t is wrong, e.g 1/(t(2)-t(1)) should give Fs but it doesn't.

Try instead:

t = T*(0:L-1);