[PYTHON] Analyse prédictive linéaire (LPC) (= analyse des formants)

Bonjour. "Analyse prédictive linéaire (LPC) (20e traitement du signal vocal en Python (2011/05/14): recherche de l'entraînement du spectre LPC) J'ai trouvé un article appelé "(= analyse des formants)", alors j'ai essayé d'exécuter le code là presque tel quel. Ceci est un exemple de la voyelle "A". a.wav.png

Le code que j'ai exécuté est le même que celui-ci, mais je vais l'écrire ( levinson_durbin.py``` est également pris à partir de là):

# coding:utf-8
from __future__ import division
import wave
import numpy as np
import scipy.io.wavfile
import scipy.signal
import pylab as P
from levinson_durbin import autocorr, LevinsonDurbin

"""Trouver le piégeage du spectre LPC"""

def wavread(filename):
    wf = wave.open(filename, "r")
    fs = wf.getframerate()
    x = wf.readframes(wf.getnframes())
    x = np.frombuffer(x, dtype="int16") / 32768.0  # (-1, 1)Normalisé à
    wf.close()
    return x, float(fs)

def preEmphasis(signal, p):
    """Filtre pré-amélioré"""
    #coefficient(1.0, -p)Créer un filtre FIR pour
    return scipy.signal.lfilter([1.0, -p], 1, signal)

def plot_signal(s, a, e, fs, lpcOrder, file):
    t = np.arange(0.0, len(s) / fs, 1/fs)
    #Trouvez le signal prédit positivement avec LPC
    predicted = np.copy(s)
    #Comme il est prédit à partir du dernier lpcOrder, l'index de départ est de lpcOrder
    #Auparavant, le signal d'origine était copié de manière imprévisible
    for i in range(lpcOrder, len(predicted)):
        predicted[i] = 0.0
        for j in range(1, lpcOrder):
            predicted[i] -= a[j] * s[i - j]
    #Tracer le signal d'origine
    P.plot(t, s)
    #Tracez le signal prédit vers l'avant avec LPC
    P.plot(t, predicted,"r",alpha=0.4)
    P.xlabel("Time (s)")
    P.xlim((-0.001, t[-1]+0.001))
    P.title(file)
    P.grid()
    P.show()
    return 0

def plot_spectrum(s, a, e, fs, file):
    #Trouvez le spectre d'amplitude du coefficient LPC
    nfft = 2048   #Nombre d'échantillons FFT
    fscale = np.fft.fftfreq(nfft, d = 1.0 / fs)[:nfft/2]
    #Spectre logarithmique du signal d'origine
    spec = np.abs(np.fft.fft(s, nfft))
    logspec = 20 * np.log10(spec)
    P.plot(fscale, logspec[:nfft/2])
    #Spectre logarithmique LPC
    w, h = scipy.signal.freqz(np.sqrt(e), a, nfft, "whole")
    lpcspec = np.abs(h)
    loglpcspec = 20 * np.log10(lpcspec)
    P.plot(fscale, loglpcspec[:nfft/2], "r", linewidth=2)
    P.xlabel("Frequency (Hz)")
    P.xlim((-100, 8100))
    P.title(file)
    P.grid()
    P.show()
    return 0

def lpc_spectral_envelope(file):
    #Charger l'audio
    wav, fs = wavread(file)
    t = np.arange(0.0, len(wav) / fs, 1/fs)
    #Découpez la partie centrale de la forme d'onde de la voix
    center = len(wav) / 2  #Numéro d'échantillon au centre
    cuttime = 0.04         #Découper la longueur[s]
    s = wav[center - cuttime/2*fs : center + cuttime/2*fs]
    #Appliquer le filtre de pré-amélioration
    p = 0.97         #Coefficient de pré-amélioration
    s = preEmphasis(s, p)
    #Fenêtre bourdonnante
    hammingWindow = np.hamming(len(s))
    s = s * hammingWindow
    #Trouvez le coefficient LPC
#    lpcOrder = 12
    lpcOrder = 32
    r = autocorr(s, lpcOrder + 1)
    a, e  = LevinsonDurbin(r, lpcOrder)
    plot_signal(s, a, e, fs, lpcOrder, file)
    plot_spectrum(s, a, e, fs, file)
    return 0

if __name__ == "__main__":
    file = "a.wav"
    lpc_spectral_envelope(file)
    exit(0)

Recommended Posts

Analyse prédictive linéaire (LPC) (= analyse des formants)
Binarisation d'images par analyse discriminante linéaire
Apprentissage automatique: analyse discriminante linéaire supervisée