2nd order high pass filter - P2prod/Filter-Modeling-Simulation GitHub Wiki

Introduction

The principle used to validate the filter is as follows:

image

The filter that is the subject of this article is simple in practice, since it can be made using 3 basic electronic components: a resistor, a capacitor and an inductor and a DC power supply.

However, the mathematical theory behind it is quite complex.

In general, this type of filter is validated by applying a unit step to the input and observing the output to check that the results are consistent with the theory. It is also possible to use a unit pulse (impulse response) or even a ramp instead.

This article will only deal with the case of the step response.

Remark: All the code examples presented in this document can be applied to the low-pass filter by modifying the numerator whic becomes simply 1.

Several methods to get the step response

There are many ways of solving the problem of the step unit response of the 2nd order high-pass filter, including the following:

  • calculation of the theoretical function using the inverse Laplace transform,

  • calculating the theoretical function by solving the ode symbolically,

  • numerical calculation using Kutta range solvers,

  • using specialised software such as Simulink or Xcos,

  • use of Excel with recurrence equations

  • ...

I'll give a few examples below.

The theory

When a unit step is applied to the filter input, the output is a function whose general equation is given below. It is rather complicated, but simplifies as soon as we assign numerical values to z and T. We then end up with exponentials, sines and cosines.

Unit step response characteristic function of a second-order high-pass filter:

$\displaystyle y(t)=-\frac{ \left(- T \cosh{\left(t \sqrt{-1 + \frac{z^{2}}{T^{2}}} \right)} + z \sinh{\left(t \sqrt{-1 + \frac{z^{2}}{T^{2}}} \right)}\right) e^{- \frac{t \cdot z}{T}}}{T \sqrt{-1 + \frac{z^{2}}{T^{2}}}}$

Simplification with z = 0.5 and T = 1.5 s :

$\displaystyle \left(-0.577 \sin(0.577 \cdot t) + 1.0 \cos(0.577 \cdot t)\right) e^{-0.333 \cdot t}$

The curve is the following one:

image

The initial value is 1 and the initial slope is $-2 \cdot \frac{z}{t}$. These values are used in the following calculations. They are intrinsically linked to the filter itself when the input is a unit step.

See more with this Jupyter Notebook : Second order high pass filter theory.ipynb

Examples of code for symbolically calculating the unit step characteristic response of a second-order high-pass filter

MATLAB

Use of Inverse Laplace instruction:

% Filtre passe-haut d'ordre 2 : réponse indicielle avec inverse laplace
clear all
syms t s T z

% inverse laplace 
transfer_function = (T^2*s^2)/(T^2*s^2 + 2*z*T*s+1)
unit_step = (1/s)
R = transfer_function*unit_step
r = ilaplace(R,s,t)

% Matlab donne r = exp(-(t*z)/T)*(cosh((t*(z^2 - 1)^(1/2))/T) - (z*sinh((t*(z^2 - 1)^(1/2))/T))/(z^2 - 1)^(1/2))

% Plot de r
z = 0.5; T = 1.5;% on définit z et T

t = linspace(0,30,100);
y = exp(-(t*z)/T).*(cosh((t*(z^2 - 1)^(1/2))/T) - (z.*sinh((t*(z^2 - 1)^(1/2))/T))/(z^2 - 1)^(1/2))% Remarque: .* pour multiplier des vecteurs

plot(t, y, 'LineWidth', 2)
title('Réponse indicielle d''un filtre passe-haut d''ordre 2')
xlabel('Temps t')
ylabel('y(t)')
grid on

Use of dsolve instruction (symbolic resolution):

% Second_order_hi_pass_filter_step_response_with_dsolve_symb
%--------------------------------------------------------------
clear all

% Paramètres
% Constante de temps T
% Coefficient d'amortissement z

% Équation différentielle
syms y(t) u(t) T z

assume(t > 0) % obligatoire sinon le clacul est impossible
u(t) = heaviside(t);

Dy = diff(y);

ode = T^2*diff(y, t, 2) + 2*z*T*diff(y, t) + y == T^2*diff(u, t, 2);

% Conditions initiales imposées par la structure intrinsèque du filtre
cond1 = y(0) == 1;
cond2 = Dy(0) == -2*z/T;

% Résolution
hold on
sol = dsolve(ode, cond1, cond2);
disp(sol)

The returned function is given below (another form but mathematically equivalent to the previous one):

$\displaystyle y(t)=\frac{e^{-\frac{t \left( z + \sqrt{(z - 1)(z + 1)} \right)}{T}} \left( z + \sqrt{(z - 1)(z + 1)} \right)}{2 \sqrt{(z - 1)(z + 1)}} -\frac{e^{-\frac{t \left( z - \sqrt{(z - 1)(z + 1)} \right)}{T}} \left( z - \sqrt{(z - 1)(z + 1)} \right)}{2 \sqrt{(z - 1)(z + 1)}}$

Numeric application

If we want to have the simplified function with the numerical values of T=1.5 and z=0.5 (and the intrinsic init conds), we have to run the following:

% Second_order_hi_pass_filter_step_response_with_dsolve
clear all
% Paramètres
T = 1.5; % Constante de temps
z = 0.5; % Coefficient d'amortissement

% Équation différentielle
syms y(t) u(t)

assume(t > 0)
u(t) = heaviside(t);

Dy = diff(y);

ode = T^2*diff(y, t, 2) + 2*z*T*diff(y, t) + y == T^2*diff(u, t, 2);

% Conditions initiales
cond1 = y(0) == 1;
cond2 = Dy(0) == -2*z/T;

% Résolution
hold on
sol = dsolve(ode, cond1, cond2);
disp(sol)

% Plot
fplot (heaviside (t), [0, 30])
fplot(sol, [0, 30])
grid on

The returned function is (numeric application):

$\displaystyle y(t)=\frac{e^{-\frac{t}{3}} \left( 3 \cos\left(\frac{\sqrt{3} , t}{3}\right) - \sqrt{3} \sin\left(\frac{\sqrt{3} , t}{3}\right) \right)}{3}$

Influence of z on the step response

2nd order hi pass Filter Step - multipe z response plot

Python code to plot the curves:

#-------------------------------------------------------------------------------
# Name:       2nd order hi pass Filter Step - multipe z response plot
# Created:     12/03/2025
#-------------------------------------------------------------------------------

import control as ct
import numpy as np
import matplotlib.pyplot as plt

T = 1.5
z_values = [0.1, 0.7, 1.5, 3]  # Liste des valeurs de z

# Créer une variable 's' pour les opérations algébriques sur les systèmes SISO
s = ct.tf('s')

# Définir l'intervalle de temps
T_sim = np.linspace(0, 100, 1000)  # de 0 à 10 s avec 1000 points

plt.figure(figsize=(10, 6))

for z in z_values:
    H = (T**2 * s**2) / (T**2 * s**2 + 2 * z * T * s + 1)  # Fonction de transfert
    t, y = ct.step_response(H, T=T_sim)  # Calcul de la réponse indicielle
    plt.plot(t, y, label=f'z={z}')  # Tracé de la courbe

# Personnalisation du graphique
plt.grid(True)
plt.legend()
plt.title('Réponse indicielle pour différentes valeurs de z')
plt.xlabel('Temps (s)')
plt.ylabel('Amplitude')

# Affichage du graphique
plt.show()