DSP Icebreaker – Drawing a Sine Wave in python of 100 Hz

So this article is for enthusiasts which have interest for Digital Signal Processing or for all those students out there willing to understand DSP but do not know where to start.

In this article I’ll show you the practical aspect of DSP, by simply drawing a sinusoidal signal in Digital domain, I will show you how all that theoretical knowledge we learn in classroom is used in implementing in something simple as a sine signal.

But before beginning, a little brush up on the concepts:

  • Sampling Frequency –

    Sampling frequency is the frequency which we sample an analog signal. We generate a train of impulses and sample the analog signal. The time period between two successive impulse is called sampling interval Tpd. And the frequency is sampling frequency ‘fs‘.

    Look at the following diagram for reference.

Sampler and Quantizer
Sampling an analogue signal x(t) with impulse train (shown above) to produce sampled signal shown in the right.

We’ll not go in depth how sampling is done, because let’s face it, that is in itself a huge mathematical mess and not the scope of article.

  • Nyquist Theorem –

Nyquist theorem says that the sampling frequency fs must be at-least two times than the maximum frequency component present in the signal.
Consider speech, we know maximum voice frequency which we can hear is around 1.5 KHz.
To sample this spectrum ranging from 20 Hz to 1.5 KHz signal, a pulse train with a sampling frequency like 8 KHz will be sufficient, because let’s not forget, our danger mark is 3 KHz as 2 x 1.5 = 3 KHz.
Typically a song stored in some disk has the sampling frequency of 48 KHz.
Remember higher is the sampling frequency, better is the resolution, but more is the memory required to save this sampled sequences and larger is the computation needed to process this data.

Now you see how all this is interconnected?

Anyways, we’ll not worry about something as complex as voice synthesis, perhaps someday day maybe. But let’s start with something very simple.
We will start with drawing a simple sinusoidal waveform. And yes, this will be worth because a sinusoidal waveform is like building block for learning practical DSP.

Let’s start –

we know an analog sine wave is given as –

x(t) = A sin(ωt)

Here ‘ω’ is angular frequency.

Alternately,

ω = 2πf

Where ‘f’ is frequency of signal.

To draw a signal with frequency 100 Hz, set f = 100 Hz (Tpd = 1/f = 0.01 seconds) and we are good to go.

In digital domain, the counterpart of ω is Ω.
Now we arrive at the most confusing part, we all must have studied that in digital domain frequencies are periodic with a period of . And ranges between

-π < Ω < π

Any frequency greater than π will wrap up somewhere in this range.
So the question is, does that mean that, as π = 3.14; we cannot draw signals other than those ranging between -3.14 Hz to +3.14 Hz
That is absurd and lame!

Now pay attention. The Ω is actually a ratio of 2 * π * f / fs. Hence from this logic

π < Ω < π
or -pi < 2 * pi * f / fs < pi
or -0.5 < f / fs < 0.5

Or in absolute terms f / fs > 0.5, i.e. fs > 2f.
This also respects Nyquist Theorem.

Suppose we want to draw a sinusoidal signal of frequency 100 Hz in digital domain. All we need to know is what was the sampling frequency. Then,

f = 100 Hz
fs = 10 KHz
Ω = 2πf / fs

Then signal would be simply –

x[n] = A sin (Ω n)

We need just one more helpful information. For how many samples should we draw this sequence.
Wonder if we take sequence such that n varies from n = 0, 1, … N-1;
Will it draw a complete sequence. Or will it repeat my sine signal many times.
It is for one this reason periodicity is helpful.

Let N be the number of samples such that exactly after N number of samples, the sine cycle will repeat.
To find this

N / m = fs /f
or N = m * fs / f

where m is so adjusted that N / m is a rational number.
Beware! not all sequences are periodic, even those signals which are periodic in analog domain, may not be periodic in digital domain.
(but this exception will not stop us from drawing, even if that is incomplete sequence)

for our example,
fs = 10 KHz = 10000 Hz,
f = 100 Hz
hence, N = 100, m = 1

Lets draw a this in python.
We will use numpy and matplotlib packages too draw sequences.

import numpy as np
import matplotlib.pyplot as plot

# sampling freq
fs = 10000

# message freq
fm = 100

# discrete frequency
w = 2 * np.pi * fm / fs

# time period
# no algo used here to find time period
N = 100

time = np.arange(0, N, 1);
amplitude = np.sin( w * time)

# plot
plot.plot(time, amplitude)

# Give a title for the sine wave plot
plot.title('Sine wave')

# Give x axis label for the sine wave plot
plot.xlabel('Time')

# Give y axis label for the sine wave plot
plot.ylabel('Amplitude = sin(time)')
plot.grid(True, which='both')
plot.axhline(y=0, color='k')
plot.show()
Adjusting the value of N = 200, we can get two complete cycles.

Alternately, if we use N = 100, but f = 50 Hz, we see two complete cycles of 50 Hz sequence.

Play with the numbers in code to explore more. See what happens if you put f more than 5 KHz for sampling frequency of 10 KHz.

That’s it!

Leave a comment