# spectrogram of a (strongly) downsampled file

I downsampled an audio file to a very low sampling rate, 48hz. This is because I stored some information in the file, that are not really audio information but the audio format was convenient to use. After we recorded the files, we realized we can strongly downsample the original file without losing audio information, because the maximum frequency present in the spectrum are around 20hz - hence we can safely downsample to 48hz.

In order to check that the downsample was sucessfull and did not loose relevant information, I plotted a librosa specshow, to see whether it looks correct. But when I do that I see a lot of higher frequencies that were not present in the specshow of the original file.

Here a few code lines, so you can see what I did and the two plots to compare:

1. downsampling: I used the scipy resample function, but I got similar results with scipy decimate.
snd, sampling_rate = sf.read(file_name)
number_of_samples = round(len(snd) * float(new_rate) / sampling_rate)
new_snd_resample = scipy.signal.resample(snd, number_of_samples)

1. specshow plotting:
snd = np.abs(librosa.stft(snd))

fig, ax = plt.subplots()
img = librosa.display.specshow(librosa.amplitude_to_db(snd, ref=np.max),
y_axis='hz', x_axis='time', ax=ax)
plt.ylim([1,1000])
ax.set_title(name)
fig.colorbar(img, ax=ax, format="%+2.0f dB")
plt.show()


And here the two resulting plots:

1. original file:

1. downsampled:

Is this maybe a problem of specshow with such a low and unusual sampling rate data? How can I check the spectral content of the downsampled file otherwise?

When I open the downsampled files, the data looks the same as the original, so I think the downsample process was correct.

## 1 Answer

If you want to display the y-axis in actual Hz you need to pass in the sample rate into librosa.display.specshow. I think the default is 22050Hz which is wrong for both plots. The time axis for both plot should be the same (since the length in physical time should not have changed) and it clearly isn't.

Your second plot makes no sense. If the data is sampled at 48Hz, the highest frequency that can be in the signal is 24 Hz.

Down sampling is not trivial. The most crucial step is to pick the right low-pass filter, which is a complicated trade off between time domain ringing, residual aliasing, phase distortion, passband flatness, etc.

How can I check the spectral content of the downsampled file otherwise?

Compare the spectra from 0 Hz to 24 Hz "before and after". Make sure that the frequency resolution of the spectrum is high enough see enough detail. At 48 Hz you only get about 20 samples per second, so I would FFT the whole thing. Depending on how your boundaries look like, you may have to window it.

• thanks for your suggestions. how can I decide the right low-pass filter? In other words, how can I check that the resulting data did not get compromise? Nov 20, 2021 at 14:39
• A) Define key criteria for "not compromised". Could be spectral magnitude, phase, time domain transients, causality, ringing, etc. Whatever is important to your application. B) Set targets for each, C) measure before and after, D) compare measurements to targets. Nov 21, 2021 at 14:41
• thanks Hilmar for your suggestions. I think I know how to measure spectral magnitude using scipy, but it is not clear to me how to measure the other audio features you listed. can I find them in scipy or are you referring to other libraries? Nov 22, 2021 at 16:16
• First you need to decide what features are important for your application. Then you can think about how to measure and specify them. It really depends on what you want to do with the data Nov 22, 2021 at 18:01
• My main concern is that frequency spectrum and magnitude are intact. Nov 23, 2021 at 12:28