Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

how can we use scipy.signal.resample to downsample the speech signal from 44100 to 8000 Hz signal?

Tags:

python

scipy

fs, s = wav.read('wave.wav')

This signal has 44100 Hz sampleing frquency, I want to donwnsample this signal to 8Khz using scipy.signal.resample(s,s.size/5.525) but the second element can't be float, so, how can we use this function for resmapling the speech signal?

How we can use scipy.signal.resample to downsample the speech signal from 44100 to 8000 Hz in python?

like image 588
Rizwan Ishaq Avatar asked May 09 '16 16:05

Rizwan Ishaq


People also ask

How does Scipy signal resample work?

The resampled signal starts at the same value as x but is sampled with a spacing of len(x) / num * (spacing of x) . Because a Fourier method is used, the signal is assumed to be periodic. The data to be resampled. The number of samples in the resampled signal.

How do I downsample a wav file in Python?

To downsample (also called decimate) your signal (it means to reduce the sampling rate), or upsample (increase the sampling rate) you need to interpolate between your data. The idea is that you need to somehow draw a curve between your points, and then take values from this curve at the new sampling rate.


1 Answers

Okay then, another solution, this one with scipy for real. Just what asked for.

This is the doc string of scipy.signal.resample():

"""
Resample `x` to `num` samples using Fourier method along the given axis.

The resampled signal starts at the same value as `x` but is sampled
with a spacing of ``len(x) / num * (spacing of x)``.  Because a
Fourier method is used, the signal is assumed to be periodic.

Parameters
----------
x : array_like
    The data to be resampled.
num : int
    The number of samples in the resampled signal.
t : array_like, optional
    If `t` is given, it is assumed to be the sample positions
    associated with the signal data in `x`.
axis : int, optional
    The axis of `x` that is resampled.  Default is 0.
window : array_like, callable, string, float, or tuple, optional
    Specifies the window applied to the signal in the Fourier
    domain.  See below for details.

Returns
-------
resampled_x or (resampled_x, resampled_t)
    Either the resampled array, or, if `t` was given, a tuple
    containing the resampled array and the corresponding resampled
    positions.

Notes
-----
The argument `window` controls a Fourier-domain window that tapers
the Fourier spectrum before zero-padding to alleviate ringing in
the resampled values for sampled signals you didn't intend to be
interpreted as band-limited.

If `window` is a function, then it is called with a vector of inputs
indicating the frequency bins (i.e. fftfreq(x.shape[axis]) ).

If `window` is an array of the same length as `x.shape[axis]` it is
assumed to be the window to be applied directly in the Fourier
domain (with dc and low-frequency first).

For any other type of `window`, the function `scipy.signal.get_window`
is called to generate the window.

The first sample of the returned vector is the same as the first
sample of the input vector.  The spacing between samples is changed
from dx to:

    dx * len(x) / num

If `t` is not None, then it represents the old sample positions,
and the new sample positions will be returned as well as the new
samples.

"""

As you should know, 8000 Hz means that one second of your signal contains 8000 samples, and for 44100 Hz, it means that one second contains 44100 samples.

Then, just calculate how many samples do you need for 8000 Hz and use the number as an second argument to scipy.signal.resample().

You may use the method that Nathan Whitehead used in a resample function that I coppied in other answer (with scaling),

or go through time i.e.

secs = len(X)/44100.0 # Number of seconds in signal X
samps = secs*8000     # Number of samples to downsample
Y = scipy.signal.resample(X, samps)
like image 99
Dalen Avatar answered Oct 21 '22 10:10

Dalen