More info about HP filters : https://www.electronics-tutorials.ws/filter/filter_3.html
Inspiration for this notebook : https://notebook.community/mholtrop/Phys605/Python/Signal/RC_Filters_in_Python
Define the function that corresponds to a low-pass RC filter :
import matplotlib.pyplot as plt
import numpy as np
def rc_high_pass_filter(f, R, C):
omega = 2*np.pi*f
return 1j*R*omega*C / (1.0 + 1j*R*omega*C)
The cutoff frequency is defined by :
def rc_high_pass_cutoff(R, C):
return 1.0/(2*np.pi*R*C)
Define the filter :
R=1.0e3 # 1kOhm
C=1.0e-6 # 1µF
fc = rc_high_pass_cutoff(R, C)
print("Filter cut off is: {:7.2f} Hz".format(fc))
Filter cut off is: 159.15 Hz
Define the square wave :
from scipy import signal
# Frequency of the square wave :
f = 50.0 # frequency in [Hz]
T = 1.0/f # period of the signal in [s]
# , total time simulated, and the sample spacing in time
# Sample points :
samples = 2**15 # a 2^N number of samples make the FFT very fast
periods = 2 # number of periods to show
delta_t = T * periods / samples # time corresponding to one sample
t = np.linspace(0, 1/f * periods, samples, endpoint=False)
y = signal.square(2*np.pi*t*f) # Create a square wave wiht a 2 Volt peak to peak (-1V to +1V)
plt.figure(figsize=(10,5))
plt.plot(1e3*t, y) # Change the x-axis scale to ms by multiplying by 10^3
ax = plt.gca()
plt.grid(True)
plt.title("Square Wave")
plt.xlabel("time(ms)",position=(0.95,1))
plt.ylabel("signal(V)",position=(1,0.9))
plt.show()
Apply the filter to the square wave :
from scipy.fftpack import fft, ifft, fftfreq, fftshift
# helper function :
def apply_filter_and_plot(R, C, samples, delta_t, y):
y_out = ifft(fft(y) * rc_high_pass_filter(fftfreq(samples, delta_t), R, C))
plt.figure(figsize=(10,5))
plt.plot(1e3*t,np.real(y_out))
ax = plt.gca()
plt.grid(True)
plt.title("Square wave with LP filter. R={:7.2f} Ohms, C={:0.2f} uF, cutoff={:0.1f} Hz".format(R, C*1e6, rc_high_pass_cutoff(R, C)))
plt.xlabel("time(ms)",position=(0.95,1))
plt.ylabel("signal(V)",position=(1,0.9))
plt.show()
apply_filter_and_plot(R, C, samples, delta_t, y)
apply_filter_and_plot(R, C/10, samples, delta_t, y)
apply_filter_and_plot(R, C*3, samples, delta_t, y)