Либроса Мел фильтр банка уменьшающихся треугольников
Я немного застрял в понимании MFCC.
Из того, что я прочитал, банки фильтров mel должны быть серией треугольников, которые становятся шире и их пики находятся в одном месте. Как это...
Однако когда я вычисляю банки фильтров mel с использованием librosa, я получаю...
Код:
mel_basis = librosa.filters.mel(sr=sr, n_fft=512, n_mels=10,fmin=0, fmax=sr / 2)
plt.plot(mel_basis)
3 ответа
Теперь я немного более информирован, и я чувствую, что полученный ответ не совсем корректен, поэтому я думаю, что должен ответить на свой вопрос.
librosa.filters.mel возвращает матрицу с формой (n_mels, n_fft/2 +1). Это означает, что каждая строка в матрице является mel. Столбцы представляют собой вес для каждой частоты для банка фильтров расплава. Частота в терминах циклов до числа n_fft, мы отбрасываем половину из них из-за псевдонимов (теорема Найквиста).
Это означает, что для правильного построения графиков матрицу необходимо транспонировать. Поскольку мы фактически хотим, чтобы N разных графиков, где N является количество мели.
plt.plot(mel.T)
Это дает следующее изображение:
Обратите внимание, что этот набор банков фильтров mel не соответствует ожиданиям. Это связано с тем, что Librosa использует нормализованную версию банков мел-фильтров, это означает, что каждый из смесей имеет площадь 1 вместо традиционной равной высоты 1. Матрица, возвращаемая из librosa, может быть преобразована в равную высоту плавления. Банк фильтров по:
mels /= np.max(mels, axis=-1)[:, None]
Вам не хватает вектора частоты, каждый фильтр имеет nftt/2 +1 выборки, поэтому основание mel представляет собой матрицу n_mels x (nfft/2 +1) в librosa.
Чтобы вычислить MFCC, вы должны получить спектр мощности сформированного сигнала, а затем умножить его на банк фильтров.
import numpy.matlib
sr = 22050
n_fft = 512
n = 10
mel_basis = librosa.filters.mel(sr=sr, n_fft=n_fft, n_mels=n,fmin=0, fmax=sr / 2)
f = np.linspace(0,sr/2,(n_fft/2)+1)
f_all = np.matlib.repmat(f, n,1)
plt.plot(f_all,mel_basis)
plt.show()
Если вы предпочитаете другой вариант печати, может использоваться цикл for.
for i in range(n):
plt.plot(f,mel_basis[i])
plt.show()
Ну, это немного поздно, но я надеюсь, что этот ответ будет полезен для всех, кто борется с различными реализациями mel-filterbank:
Существует несколько различных реализаций mel-filterbanks; В частности, librosa имеет 2 разных: один из набора инструментов скрытой марковской модели (HTK) в Кембридже, и он по умолчанию написан Slaney и реализован также в Audlaory Toolbox Matlab:
HTK генерирует набор фильтров со всеми фильтрами, установленными с усилением 1 в его центре. Slaney генерирует нормализованный фильтр, который может быть нормализован по площади или полосе пропускания.
Кроме того, их эффективность очень похожа, значения фильтров не одинаковы, поэтому я сомневаюсь, что изменение визуализации может быть полезным.
Обратитесь к этому документу для получения дополнительной информации о сравниваемой производительности различных реализаций mel-filterbak.
Вы ищете "Банк мел-фильтров с такой же высотой банка". Я тоже ищу это. Сначала нужно транспонировать mels, просто используйте параметр "norm" и измените его на None.
mels = librosa.filters.mel(20000, 2048, n_mels=4, fmin=0.0, fmax=None, htk=False, norm=None)
plt.plot(mels.T)
plt.show()