Ajout stft-decode

这个提交包含在:
Mattéo Delabre 2020-12-20 01:36:12 +01:00
父节点 708b3ef4d7
当前提交 d124e8465e
签署人:: matteo
GPG 密钥 ID: AE3FBD02DC583ABB
共有 3 个文件被更改,包括 38 次插入5 次删除

查看文件

@ -13,10 +13,10 @@ Une première approche consiste à étudier le spectre du signal en utilisant un
![Spectre du son produit par le synthétiseur](fig/synth-fft.png) ![Spectre du son produit par le synthétiseur](fig/synth-fft.png)
Ce spectre permet de lire les différentes fréquences qui composent le son étudié. Sur ce spectre peuvent être distinguées les douze notes qui composent le morceau :
On y distingue, parmi les fréquences les plus représentées, un *sol₂* (192 Hz), un *do₂* (131 Hz), un *la₂* (220 Hz) et un *la₃* (440 Hz). _do₂, sol₂, la₂, do₃, mi₃, fa₃, sol₃, la₃, si₃, do₄, re₄, mi₄._
Une information cruciale manque cependant, celle de l’évolution du signal dans le temps. Une information cruciale manque cependant, celle de l’évolution du signal dans le temps.
Une façon de l’obtenir consiste à découper le signal en courtes fenêtres de temps et d’appliquer la transformation de Fourier sur les morceaux obtenus : c’est [la transformée de Fourier à court terme](https://fr.wikipedia.org/wiki/Transform%C3%A9e_de_Fourier_%C3%A0_court_terme). Une façon de l’obtenir consiste à découper le signal en courtes fenêtres de temps et d’appliquer la transformation de Fourier sur les segments obtenus : c’est [la transformée de Fourier à court terme](https://fr.wikipedia.org/wiki/Transform%C3%A9e_de_Fourier_%C3%A0_court_terme).
On obtient ainsi un [sonagramme](https://fr.wikipedia.org/wiki/Sonagramme) qui montre l’évolution des fréquences du signal dans le temps (produit par [ce script Python](stft-graph.py)). On obtient ainsi un [sonagramme](https://fr.wikipedia.org/wiki/Sonagramme) qui montre l’évolution des fréquences du signal dans le temps (produit par [ce script Python](stft-graph.py)).
![Évolution dans le temps du spectre du son produit par le synthétiseur](fig/synth-stft.png) ![Évolution dans le temps du spectre du son produit par le synthétiseur](fig/synth-stft.png)

查看文件

@ -14,10 +14,10 @@ source_file = sys.argv[1]
# Calcul du FFT # Calcul du FFT
signal = soundbox.load_signal(source_file) signal = soundbox.load_signal(source_file)
freq_scale = soundbox.samp_rate / len(signal)
vecs = np.fft.fft(signal)[:soundbox.samp_rate // 2] vecs = np.fft.fft(signal)[:soundbox.samp_rate // 2]
values = np.absolute(vecs) / np.max(np.absolute(vecs)) values = np.absolute(vecs) / np.max(np.absolute(vecs))
freq_scale = soundbox.samp_rate / len(signal)
freq = np.arange(len(values)) freq = np.arange(len(values))
# Calcul de la fenêtre des fréquences intéressantes # Calcul de la fenêtre des fréquences intéressantes

33
stft-decode.py 普通文件
查看文件

@ -0,0 +1,33 @@
import soundbox
import numpy as np
import scipy.signal as sig
import sys
if len(sys.argv) != 2:
print(f"""Utilisation: {sys.argv[0]} [source]
Détermine les notes jouées dans le fichier [source] en utilisant
la transformation de Fourier à court terme.""")
sys.exit(1)
source_file = sys.argv[1]
# Calcul du STFT
signal = soundbox.load_signal(source_file)
freq, time, vecs = sig.stft(signal, soundbox.samp_rate, nperseg=soundbox.samp_rate * 0.25)
values = np.absolute(vecs) / np.max(np.absolute(vecs))
time_scale = len(signal) / soundbox.samp_rate / values.shape[1]
# Calcul de la fenêtre des fréquences intéressantes
high_enough = np.where(values.max(axis=1) >= 0.01)
left = high_enough[0][0]
right = high_enough[0][-1]
freq = freq[left:right]
values = values[left:right]
# Recherche des pics
for i in range(values.shape[1]):
peaks, _ = sig.find_peaks(values[:, i], height=0.1, distance=10)
print(f'{i * time_scale:.2f} s', list(map(soundbox.freq_note, freq[peaks])))