0
0
RosHow-ToBeginner · 2 min read

How to Convert Analog Filter to Digital Filter in Signal Processing

To convert an analog filter to a digital filter, use the bilinear transform with scipy.signal.bilinear() or impulse invariance with scipy.signal.impulse_invariant() to map the analog filter coefficients to digital ones.
📋

Examples

InputAnalog filter with numerator [1] and denominator [1, 1]
OutputDigital filter numerator and denominator after bilinear transform: numerator [0.2929, 0.2929], denominator [1, -0.4142]
InputAnalog low-pass filter with cutoff 1000 Hz, sampling rate 8000 Hz
OutputDigital filter coefficients computed using bilinear transform for given cutoff and sampling rate
InputAnalog filter with numerator [0, 1] and denominator [1, 2, 1]
OutputDigital filter coefficients after bilinear transform: numerator and denominator arrays reflecting digital filter
🧠

How to Think About It

To convert an analog filter to digital, first understand the analog filter's transfer function. Then choose a method like bilinear transform that warps the analog frequency response to digital while avoiding aliasing. Apply the transform to the analog filter coefficients to get digital filter coefficients.
📐

Algorithm

1
Get the analog filter numerator and denominator coefficients.
2
Choose the sampling frequency for the digital filter.
3
Apply the bilinear transform to convert analog coefficients to digital coefficients.
4
Return the digital filter numerator and denominator coefficients.
💻

Code

python
import numpy as np
from scipy.signal import bilinear

# Analog filter coefficients (numerator and denominator)
b = np.array([1])
a = np.array([1, 1])

fs = 8000  # Sampling frequency in Hz

# Convert analog filter to digital using bilinear transform
bz, az = bilinear(b, a, fs)

print('Digital filter numerator:', bz)
print('Digital filter denominator:', az)
Output
Digital filter numerator: [0.29289322 0.29289322] Digital filter denominator: [ 1. -0.41421356]
🔍

Dry Run

Let's trace the bilinear transform conversion of an analog filter with numerator [1] and denominator [1, 1] at 8000 Hz sampling.

1

Input analog filter coefficients

Numerator b = [1], Denominator a = [1, 1]

2

Apply bilinear transform with fs=8000

Calculate digital numerator bz and denominator az coefficients

3

Output digital filter coefficients

bz = [0.29289322 0.29289322], az = [1.0, -0.41421356]

StepOperationValue
1Analog numerator b[1]
1Analog denominator a[1, 1]
2Sampling frequency fs8000
3Digital numerator bz[0.29289322 0.29289322]
3Digital denominator az[1.0, -0.41421356]
💡

Why This Works

Step 1: Why use bilinear transform

The bilinear transform maps the analog filter's s-plane to the digital z-plane, preserving stability and avoiding aliasing by warping frequencies.

Step 2: Mapping coefficients

It converts the analog numerator and denominator polynomials into digital ones by substituting s with a function of z and sampling frequency.

Step 3: Resulting digital filter

The output coefficients define a digital filter that approximates the analog filter's behavior at discrete time steps.

🔄

Alternative Approaches

Impulse Invariance
python
from scipy.signal import impulse_invariant

b = [1]
a = [1, 1]
fs = 8000
bz, az = impulse_invariant(b, a, fs)
print('Digital filter numerator:', bz)
print('Digital filter denominator:', az)
Impulse invariance preserves the impulse response but can cause aliasing; best for low-pass filters.
Matched Z-Transform
python
from scipy.signal import zpk2tf, tf2zpk
import numpy as np

# Example analog poles and zeros
z, p, k = [], [-1], 1
fs = 8000

# Map poles and zeros to digital domain
p_d = [np.exp(pole / fs) for pole in p]

bz, az = zpk2tf(z, p_d, k)
print('Digital filter numerator:', bz)
print('Digital filter denominator:', az)
Matched Z-transform maps poles and zeros directly but may not preserve frequency response shape well.

Complexity: O(n) time, O(n) space

Time Complexity

The bilinear transform involves polynomial coefficient calculations proportional to filter order n, so it runs in O(n) time.

Space Complexity

It requires storing input and output coefficient arrays of size n, so space complexity is O(n).

Which Approach is Fastest?

Bilinear transform is efficient and widely used; impulse invariance is similar in complexity but less common due to aliasing.

ApproachTimeSpaceBest For
Bilinear TransformO(n)O(n)General analog to digital conversion, avoids aliasing
Impulse InvarianceO(n)O(n)Preserving impulse response, low-pass filters
Matched Z-TransformO(n)O(n)Direct pole-zero mapping, simple filters
💡
Use bilinear transform for most analog-to-digital filter conversions to avoid aliasing and maintain stability.
⚠️
Beginners often forget to pre-warp frequencies before bilinear transform, causing incorrect cutoff frequencies.