На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
Модераторы: RaD, nsh
Страницы: (5) [1] 2 3 ... Последняя » все  ( Перейти к последнему сообщению )  
> Вычисление мел-кепстра и распознавние DTW , Подробности реализации
    Привет братьям по несчастью =) Перед мной тоже стоит задача сравнить два файла (записаных с микрофона), содержащие одну и ту же фразу. Я делаю так:

    1 Считываю файлы (по 2с) Частота дискретизации = 12КГц
    2 Обрезаю лишнее (шум) остается приблизительно 1/3 сигнала
    3 Делю их на фреймы (кадры) по 20мс с перекрытием в 2/3

    3.1 Беру один фрейм. Применяю к нему "pre-emphasise". Формула:
    v(n) = s(n) - a * s(n - 1),
    где s(n) - исходный сигнал, а - переметр фильтрации (0.9375), v(n) - отфильтрованный сигнал.

    3.2 Умножаю фрейм на окно Хемминга. Формула:
    f(i) = y(i) * w(i),
    y(i) - исходный сигнал, w(i) - оконная функция:
    w(n) = 0.54 - 0.46 * cos(2 * pi * (n - 1) / (N - 1)); (n = 0..N)
    N - кол-во отсчетов оконной функции. Оно равно длине фрейма.

    3.3 Произвожу БПФ(600)
    12КГц / 20мс = 600 отсчетов (300 в одну сторону и 300 симметричных)

    3.4 Далее формирую 300 пар по принципу описаного в этой теме:
    s(k) = y(k) ^ 2 + y((N + 1) - k) ^ 2; (k = 1..300; N = 600)
    Первый с последним, второй с предпоследним и т д

    3.5 Логаифмирую: s_log(k) = log(s(k));

    3.6 Взял 24 частоты.
    FHZ = [20,100,200,300,400,510,630,770,920,1080,1270,1480,1720,2000,2320,2700,3150,3700,4400,5300,6400,7700,9500,12000];
    Перевожу их в МЕЛ-шкалу:
    mel(i) = 1127 * log(1 + FHZ(i) / 700); (i = 1..24)

    3.7 Усредняю (взятое из той же темы)
    ExpandedWrap disabled
      Fs = 12000 / 300;
      for j = 2:23
          kj = round(FHZ(j) / Fs);
          kl = round(FHZ(j - 1) / Fs);
          kr = round(FHZ(j + 1) / Fs);
          l = kj - kl;
          r = kr - kj;
          Aj = 0;
          
          for i = 1:l
              mi = i / l;
              Aj = Aj + s_log(kl + i) * mi;
          end
          for i = 1:r - 1
              mi = i / r;
              Aj = Aj + s_log(kr - i) * mi;
          end
          A(j) = Aj / (l + r - 1);
      end

    3.8 Вычисление кепстральных коеффициентов (КК) через cos-преобразование:
    N - кол-во СПЕКТРальных коеф. = 22 (без двух крайних)
    ExpandedWrap disabled
      for k = 1:12
          c(k) = 0;
          for i = 2:23
              c(k) = c(k) + A(i) * cos(pi * k * (2 * (i - 1) + 1) / 2 / N);
          end
      end

    4 Сравнение с помощью DTW:
    D(x,y) = sqrt(sum( (x[i] - y[i])^2 ) );
    x - входной вектор
    y - эталонный вектор словаря

    ----------------------------
    Подвожу итог: в результате этих всех преобразований мы получим по 12 КК для каждого фрейма. А фреймов у меня (с перекрытием 2/3) в обрезаном сигнале 88. Тоесть получается матрица 12х88. Тоже самое я делаю для другого звукового сигнала. Проделав это все ничего не получается. Например слово "восемь" одинаково похоже на слово "девять", "восемь". Кстати графики получившихся КК визуально пхожи друг на друга формой. Если нужно я могу выложить графический результат любого шага.
    ----------------------------
    * Может я DTW неправильно делаю, или мне нужно взять другой метод сравнивания?
    * Может нужно сперва сделать pre-emphasise и Хемминга для всего сигнала, а потом только брать опять по одному фрейму и делать 3.3...3.8 ?
    * Я так и не понял что делать частотами, переведенными в мел шкалу. Пункт 3.6
    * Кол-во отсчетов БПФ влияет както на распознавание? И правильно ли я подобрал их кол-во?
    * Правильно ли я подсчитал Fs?

    Эта тема была разделена из темы "Нормирование речевого сигнала"
      В целом всё правильно вроде

      Цитата
      3.5 Логаифмирую: s_log(k) = log(s(k));


      Обычно логарифмы берут уже от результатов фильтрации гребенки. В этом случае всего 20 логарифмов нужно посчитать, а не 300.

      Цитата
      где s(n) - исходный сигнал, а - переметр фильтрации (0.9375), v(n) - отфильтрованный сигнал.


      Обычно 0.97 фильтрация

      Цитата
      Может я DTW неправильно делаю, или мне нужно взять другой метод сравнивания?


      DTW подразумевает прямой и обратный проходы, вы их точно делаете? У Вас только формула написана одна.
        Цитата nsh @
        Цитата
        где s(n) - исходный сигнал, а - переметр фильтрации (0.9375), v(n) - отфильтрованный сигнал.

        Обычно 0.97 фильтрация

        Что значит "обычно"? Мне например больше нравится коэффициент 0.5 Это как хорошо или плохо? По идее точность распознования должна меняться с изменением этого коэффициента. nsh, вы много чего читали и читаете, может вы сможете прояснить этот вопрос?
        Сообщение отредактировано: KoPoBuH -
          Цитата
          3.3 Произвожу БПФ(600)
          12КГц / 20мс = 600 отсчетов (300 в одну сторону и 300 симметричных)


          Это как так? Ведь 20мс при частоте 12 000Гц - это 240 отсчётов.
          12 000 - 1000мс
          x - 20мс

          х = 240;
            Цитата

            Что значит "обычно"? Мне например больше нравится коэффициент 0.5 Это как хорошо или плохо? По идее точность распознования должна меняться с изменением этого коэффициента. nsh, вы много чего читали и читаете, может вы сможете прояснить этот вопрос?


            Этот фильтр для предусиления высоких частот используется, собственно и коэффициент фильта подобран, чтобы нужные частоты предусиливались. Я так понимаю, там 6dB на 3kHz как раз получается. Никогда не смотрел точно. Ещё недавно читал, что такое предусиление не особо нужно, потому что его эффект затем нормализацией CMN убирается.

            Для меня полезность такого фильтра только в том, что он DC убирает, поэтому его перед простым VAD считающим энергию ставить можно.
              Цитата
              Обычно логарифмы берут уже от результатов фильтрации гребенки. В этом случае всего 20 логарифмов нужно посчитать, а не 300.

              Сделал, теперь логарифмирую после усреднения.

              Цитата
              Обычно 0.97 фильтрация

              Я нашол на форуме ссылку на сайт, там лежат исходники. Судя по коду их писали здоровые дядьки. Я решил полностью им доверится. Так вот у них этот коэффициент равен 0.9375

              Цитата
              DTW подразумевает прямой и обратный проходы, вы их точно делаете? У Вас только формула написана одна.

              А насчет DTW - видимо я гдето недочитал, буду разбираться.

              Парочка вопросов:
              * Кол-во отсчетов БПФ влияет на точность распознавания?
              * Вы так и не ответили зачем нужен перевод в МЕЛ-шкалу (пункт 3.6)?
              Можетбыть далее при усреднении (пункт 3.7) вместо массива FHZ = [20,100,200...7700,9500,12000] нужно использовать массив МЕЛ-частот m[]?
              ExpandedWrap disabled
                ...
                for j = 2:23
                    kj = round(FHZ(j) / Fs);
                    kl = round(FHZ(j - 1) / Fs);
                    kr = round(FHZ(j + 1) / Fs);
                    l = kj - kl;
                    r = kr - kj;
                ...
                Цитата
                3.4 Далее формирую 300 пар по принципу описаного в этой теме:
                s(k) = y(k) ^ 2 + y((N + 1) - k) ^ 2; (k = 1..300; N = 600)
                Первый с последним, второй с предпоследним и т д


                Поясните, зачем первый с последним, второй с предпоследним.
                Может быть просто
                Цитата
                s[k}=a[k]*a[k]+b[k]*b[k]; (для всех k)
                (из поста Анатоля ) исходя их ссылки в вашем пункте 3.4
                Как я понимаю просто находим модуль комплексного числа которым является результат FFT z = x+iy z*z = x*x+y*y
                  Цитата nsh @
                  Этот фильтр для предусиления высоких частот используется, собственно и коэффициент фильта подобран, чтобы нужные частоты предусиливались.

                  У любого цифрового фильтра коэффициенты могут быть любые. Это зависят в первую очередь от того, какую частотную характеристику вы хотите получить на выходе. Если вы собираетесь использовать этот же фильтр (т.е. ту же самую АЧХ) с другой тактовой частотой, коэффициенты необходимо пересчитывать. "Обычно 0.97" это глупость.

                  Этот фильтр полностью убирает DC только при коэффициенте 1.0. При всех прочих DC остается. Цель использования этого фильтра - скорректировать АЧХ речи, которая в среднем имеет характеристику -6дБ/окт. Гораздо лучше с этим справляется оыбчный ФВЧ первого порядка, у которого характеристика +6дБ/окт и на выходе ни при каких уловиях не может быть DC
                  Сообщение отредактировано: KoPoBuH -
                    mjpronin, вы хотите сказать, что a[k] - истенная часть, а b[k] - мнимая? И мне нужно вместо того, как я делал раньше:
                    ExpandedWrap disabled
                      a[1]*a[1] + b[300]*b[300]
                      a[2]*a[2] + b[299]*b[299]
                      ...
                      a[148]*a[148] + b[151]*b[151]
                      a[149]*a[149] + b[150]*b[150]

                    где a[k], b[k] - один и тотже массив

                    сделать вот так:
                    ExpandedWrap disabled
                      a[1]*a[1] + b[1]*b[1]
                      a[2]*a[2] + b[2]*b[2]
                      ...
                      a[149]*a[149] + b[149]*b[149]
                      a[150]*a[150] + b[150]*b[150]

                    где a[k] - истенная часть, а b[k] - мнимая. (k =1..150). Тогда выходит вторую часть спектра мы вобще не трогаем. Я правильно понимаю?

                    Если чесно, то я незнаю как правельнее, пусть нам подскажут эксперты =)
                      Цитата -unGod
                      Если чесно, то я незнаю как правельнее, пусть нам подскажут эксперты =)


                      В разных процедур вычисления БПФ выходные даные могут размещатся в различном порядке.
                      Обычно в таком: а0,б0,а1,б1,а2,б2...
                      Но могут и иначе.
                      Если Ви не знаете что выдает на выходе ваша процедура БПФ, то эксперементируйте. Подайте на вход известный сигнал (синус определённой частоты) и смотрите, что на выходе.
                        Цитата
                        Если вы собираетесь использовать этот же фильтр (т.е. ту же самую АЧХ) с другой тактовой частотой, коэффициенты необходимо пересчитывать. "Обычно 0.97" это глупость.


                        Да, тут я был неправ.

                        Цитата
                        Гораздо лучше с этим справляется оыбчный ФВЧ первого порядка, у которого характеристика +6дБ/окт и на выходе ни при каких уловиях не может быть DC


                        Согласен.

                        Цитата
                        Вы так и не ответили зачем нужен перевод в МЕЛ-шкалу (пункт 3.6)?


                        Мел шкала использовалась, чтобы получить параметры гребёнки фильтров

                        FHZ = [ 20,100,200,300,400,510,630,770,920,1080,1270,1480,1720,2000,2320,2700,3150,3700,4400,5300...

                        У Вас они уже заданы в табличном виде, а можно было их вычислить по вышеприведённой формуле.
                          KoPoBuH
                          Цитата
                          Гораздо лучше с этим справляется оыбчный ФВЧ первого порядка, у которого характеристика +6дБ/окт и на выходе ни при каких уловиях не может быть DC

                          А не могли ли Вы чуть подробней пояснить, какой вид имеет обычный ФВЧ первого порядка, у которого.....?


                          Просто я если и использовал фильтры в своих работах, то обычно использовал полосовые 4 порядка или ФНЧ(ФВЧ) 2 порядка с передаточной функцией апроксимированной полиномами чебышева второго рода, генерацию коэфициентов производил в Matlab, благо там это просто. Хотя всегда подозревал, что можно попробовать что-то другое :)
                            Цитата KoPoBuH @
                            Если вы собираетесь использовать этот же фильтр (т.е. ту же самую АЧХ) с другой тактовой частотой, коэффициенты необходимо пересчитывать. "Обычно 0.97" это глупость.


                            1. АЧХ этих фильтров сколько-нибудь заметно отличаются только на самых низких частотах:
                            для 8кГц на 100 герцах отличие около 1 дБ
                            для 20кГц на 100 герцах-~4 дБ, на 200 герцах - ~2дБ.

                            дальше - меньше.

                            2. Пересчитывать надо, если собираетесь использовать одни и те же модели на всех частотах квантования, чего никто не делает.
                            И вообще, пересчитывать - это слишком громко сказано. Можно минуты за 3 подобрать коэффициент, который обеспечит совпадение АЧХ на нижних частотах для любых частот квантования.

                            3.Самое главное:
                            Цитата nsh @
                            такое предусиление не особо нужно, потому что его эффект затем нормализацией CMN убирается.

                            И правильно, тем более, что абсолютная величина признаков при вероятностном подходе роли не играет - PDF будет такой же.

                            Так что 0.97 - это традиция из времён ДП, которая ничего не стоит и лишь выравнивает спектр для более удобного обозрения.
                            Кстати, эта операция, проведённая в частотной области, меньше шумит. Так что можно преобразовывать прямо
                            спектр и забыть про мягкое дифференцирование.

                            Цитата -unGod- @
                            зачем нужен перевод в МЕЛ-шкалу (пункт 3.6)?
                            - опять для понижения размерности - подробный спектр на высоких частотах не содержит различительных признаков и не воспринимается слухом. См. работы по речевосприятию.
                            Сообщение отредактировано: nsh -
                              И вообще, пересчитывать - это слишком громко сказано. Можно минуты за 3 подобрать коэффициент, который обеспечит совпадение АЧХ на нижних частотах для любых частот квантования

                              Чистой воды схоластика - мы не будем расчитывать, мы будет подбирать

                              Так что 0.97 - это традиция из времён ДП, которая ничего не стоит и лишь выравнивает спектр для более удобного обозрения.
                              Кстати, эта операция, проведённая в частотной области, меньше шумит. Так что можно преобразовывать прямо
                              спектр и забыть про мягкое дифференцирование.


                              Традиция переросшая в религию

                              Кстати, эта операция, проведённая в частотной области, меньше шумит

                              Интересно знать откуда берутся дополнительные шумы при линейной операции.

                              iitta, я не понимаю ваш странный способ опровергать, пересказывая своими словами то, что вы опровергаете
                              Сообщение отредактировано: KoPoBuH -
                                Перевод в МЕЛ-шкалу, я задействовал нужным образом.

                                А тот пункт 3.4 (из первого поста). Я просто взял из 300 отсчетов ровно половину и повозносил их в квадрат. Поскольку взять отдельно истенную и мнимую часть неполучилось =(

                                Наборы КЕПСТРальных коэффициентов у меня получились похожие на глаз. А вот алгоритм DTW их не сильно "одобряет". Напимер, слова "один", "три", "четыре", "семь", "восемь", "девять" - распознает с вероятностью в диапазоне 35%..60%, а вот слово "пять" путает с "семь". У "шесть" и "три" процент очень мал.

                                Из всего вышепроделанного я понял, что для хорошего распознавания команды нужно правильно ее отделить от шума. Ведь при обрезании возможен такой случай когда шум обрежится некоректно и в результате мы можем получить команду с небольшим хвостиком шума сзади, например. Эта ошибка может сильно повлиять на распознавание. Так как при распознавании эталона - хвостика небыло.

                                И еще один момент. Я много где читал, что люди доводили распознавание аж до 97%. А у меня ели ели 60% и незнаю как улучшить =(

                                Будьте любезны, напишите свои мнения по этому поводу
                                0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)
                                0 пользователей:


                                Рейтинг@Mail.ru
                                [ Script execution time: 0,0488 ]   [ 15 queries used ]   [ Generated: 2.05.24, 17:33 GMT ]