Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Как определить точную частоту звукового сигнала, какой алгоритм лучше использовать ? 
:(
    Опции темы
Kpeved
Дата 11.4.2012, 21:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



Так . Ещё раз прочитал код и опять не понял - что значит вот эта строчка :
Цитата

67:  X2(i)= X1(i)*DCONJG (FX(i))    !  DCONJG  - комплексное сопряжение

X2 и X1 у нас структуры , содержащие реальную и мнимую части , а не фазу и модули . Так ?   Комплексное сопряжение DCONJG всего лишь меняет знак на противоположный .Верно?  
Что тогда делает оператор * ?  Это какое то умножение , или свертка , или ещё что то ? Можно про это поподробнее .


И как то все просто в этом случае 
Цитата

72:     er=CDABS(X1(N/2))/CDABS(X1(1))

Т.есть мы берём прямое , обратное фурье только для того чтобы взять и разделить модули от N/2 -го и 1го элементов массива X1 ? Или я тут тоже что то не понимаю ? 



И вот по этому ещё :
Цитата

df=-0.69019186E+01*er+ 0.68520498E+01

Как эти цифры в нормальном виде записать ? Там , с кучей нулей впереди , или наоборот .
PM MAIL   Вверх
ramateur
Дата 12.4.2012, 15:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 1
Регистрация: 12.4.2012

Репутация: нет
Всего: нет



Доброго времени суток!

Занимаюсь обработкой речи, недавно тоже была проблема определения частоты основного тона. По ходу ковыряний в этой теме выяснил, что принципы для голоса и монофонических музыкальных звуков (звук одной струны в случае гитары) по сути одни и те же.

В связи с этим предлагаю метод YIN для задачи Kpeved'а. Описание его тут: Статья про метод YIN.

У мну получился такой код для Matlab:
Код

function F=f0yin(frame,Fs,flow,fhigh)
framelen=length(frame);
ntaumin=floor(0.9/fhigh*Fs)+1;               %мин. предел поиска периода ОТ
ntaumax=ceil(1.1/flow*Fs)+1;                 %макс. предел поиска периода ОТ
G=abs(fft(frame)).^2;                              %расчёт спектра мощности
R=1/framelen*real(ifft(G));                       %расчёт автокорреляционной ф-и
    D=R(1)-2*R(1:ntaumax);                      %описание D и D2 - в статье (там d и d')
    D2=zeros(1,ntaumax-ntaumin+1);
    for i=1:ntaumax
        j=i:framelen;
        D(i)=D(i)+1/framelen*sum(frame(j).^2);
        if i>=ntaumin
            D2(i-ntaumin+1)=D(i)./(sum(D(1:i))./i);
        end
    end
    nminD2=find(D2(2:ntaumax-ntaumin)==min(D2(2:ntaumax-ntaumin)))+1;
nminD2=nminD2(1);
%parabolic interpolation for achieving subsample accuracy
Ninterp=21;
D2interp=pinterp([nminD2-1,nminD2,nminD2+1],D2([nminD2-1,nminD2,nminD2+1]),nminD2-1:2/(Ninterp-1):nminD2+1);
nminD2interp=find(D2interp==min(D2interp));
nminD2interp=nminD2interp(1);
nminD2fine=nminD2-1+(nminD2interp-1)*2/(Ninterp-1)+(ntaumin-1);
F=Fs/(nminD2fine-1);
end


Функция принимает в качестве параметров frame – короткий фрагмент сигнала (30...80 мс), частоту дискретизации Fs и пределы полосы, где ищем частоту основного тона (открытых струн гитары с запасом сгодится flow=60, fhigh=400).

Даже при частоте дискретизации 48 кГц ошибка дискретизации для первой струны может составить около

330—1/(1/330+1/48000)=2,25 Гц,

поэтому для повышения точности поиска минимума функции D2 прикручена параболическая интерполяция:

Код

function Y=pinterp(x,y,X)
a=((y(3)-y(1))*(x(2)-x(1))-(y(2)-y(1))*(x(3)-x(1)))/...
  ((x(3)^2-x(1)^2)*(x(2)-x(1))-(x(2)^2-x(1)^2)*(x(3)-x(1)));
b=(y(2)-y(1)-a*(x(2)^2-x(1)^2))/(x(2)-x(1));
c=y(1)-a*x(1)^2-b*x(1);
Y=a*X.^2+b*X+c;
end


Возможно пригодится...
PM MAIL   Вверх
Kpeved
Дата 13.4.2012, 13:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



ramateur, да , для одной струны этот метод прокатит . я думаю что все тюнеры которые за долю секунды определяют частоту  работают с автокорелляцией . Но для множества струн он не подходит . 
PM MAIL   Вверх
Santik
Дата 13.4.2012, 15:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 13.3.2012
Где: Мирный (Якутия)

Репутация: нет
Всего: нет



67:   Да, это умножение двух векторов, один из которых комплекно сопряженный. Если сделать потом обратное Фурье - получим взаимную корреляцию .
72:  Да, мы делаем прямое и обратное преобразование для того чтобы взять потом 2 элемента массива.  Зато потом формула простая... Это чтобы с кардинальным синусом не возится.

А последнего вопроса я как-то не понял...

Это сообщение отредактировал(а) Santik - 13.4.2012, 15:59
PM MAIL   Вверх
Kpeved
Дата 13.4.2012, 18:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



Santik, т.есть в  67 формула будет такой : (a+bi)·(a′+b′i)= (a·a′−b·b′)+(a·b′+b·a′)i     . Верно? 

Хм . нормальном значит в .. обычном  , поянтным для компилятора, и для человека ) . Ну тоесть -0.69019186E+01 - это число умноженное на Е + 01 , или + 0.1 , или это Е в степени 01  ... Вобщем , как записать  это число , не используя буквы Е . 
PM MAIL   Вверх
Santik
Дата 13.4.2012, 18:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 13.3.2012
Где: Мирный (Якутия)

Репутация: нет
Всего: нет



Цитата(Kpeved @ 13.4.2012,  18:13)
Santik, т.есть в  67 формула будет такой : (a+bi)·(a′+b′i)= (a·a′−b·b′)+(a·b′+b·a′)i     . Верно? 

Хм . нормальном значит в .. обычном  , поянтным для компилятора, и для человека ) . Ну тоесть -0.69019186E+01 - это число умноженное на Е + 01 , или + 0.1 , или это Е в степени 01  ... Вобщем , как записать  это число , не используя буквы Е .


Да,  верно. В 67 все числа комплексные. Только надо все-таки сделать для второго операнда комплекное сопряжение - т.е. изменить знак мнимой части.

E - это 10.  E+01 - это 10 в степени 1.
 -0.69019186E+01 =-6.9019186

Это сообщение отредактировал(а) Santik - 13.4.2012, 18:56
PM MAIL   Вверх
Kpeved
Дата 14.4.2012, 19:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



Наконец то проверил . Деля модуль N/2 числа из конченого массива на модуль 1го числа мы всегда получаем Er = 1 . Потому что их значения одинаковые .  Поэтому результаты неправильные .  Разве только .. неправильная трактовка элементов массива . В фортране эл-ты массива начинаются с 1го или с 0го элемента ? 
PM MAIL   Вверх
Santik
Дата 15.4.2012, 16:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 13.3.2012
Где: Мирный (Якутия)

Репутация: нет
Всего: нет



Цитата(Kpeved @ 14.4.2012,  19:26)
 В фортране эл-ты массива начинаются с 1го или с 0го элемента ?

В Фортране с первого.
PM MAIL   Вверх
Kpeved
Дата 16.4.2012, 02:01 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



Все , решил . проблемма как всегда была в приведении типов в С . Проверял на сигнале генератора в 300 Гц  - значения скачут с 302 до 288 Гц , причем последовательно то уменшается , то увеличивается . Вобщем  smile 
PM MAIL   Вверх
Santik
Дата 16.4.2012, 06:06 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 13.3.2012
Где: Мирный (Якутия)

Репутация: нет
Всего: нет



A частоту в ЛЧМ- сигнале в каких пределах менял? При fd=44100 и N= 44100 надо 0.5 Гц
При fd=8000 и N= 1024 надо 0.5*8000/1024
Сигнал 300 гц вышли, посмотрим  smile 
PM MAIL   Вверх
Kpeved
Дата 16.4.2012, 15:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



ЛЧМ имеется ввиду  df ? Поменял , все равно ничего не изменилось .

Вот мои сигналы в txt . Кодировка вроде  младший , потом старший .   http://dl.dropbox.com/u/29529555/8k%20gen.rar
PM MAIL   Вверх
Kpeved
Дата 16.4.2012, 16:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



Что то меня вообще частотные методы смущают . Медленные и недостаточная точность , и разброс значений больтшой . За секунду меняет значения на +- 100 Гц (очень сильно плавает по гармоникам ).     Думаю надо попробовать с корреляцией . И вот самый главный вопрос - можно ли выловить 6 частот из сигнала , если их приблизительно знать (забитый строй +- )
PM MAIL   Вверх
Santik
Дата 17.4.2012, 07:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 13.3.2012
Где: Мирный (Якутия)

Репутация: нет
Всего: нет



Цитата(Kpeved @ 16.4.2012,  16:49)
Что то меня вообще частотные методы смущают ...    Думаю надо попробовать с корреляцией ...

Так в принципе всё, что до этого делалось - это корреляционные методы. Частотный метод (с уточнением) предлагал только Vedun. В остальных FFT используется для быстрого вычисления функции взаимной корреляции...
И полифонический сигнал я смотрел (см. выше) 
PM MAIL   Вверх
Santik
Дата 18.4.2012, 18:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 13.3.2012
Где: Мирный (Якутия)

Репутация: нет
Всего: нет



Открыл файл 8000gen300.txt  Что- то не похоже на запись синуса!!!
PM MAIL   Вверх
Kpeved
Дата 19.4.2012, 00:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 26.2.2012

Репутация: нет
Всего: нет



Santik, не знаю , сигнал сгенерирован генератором и записан . Генератор генерировал синус )
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Алгоритмы"

maxim1000

Форум "Алгоритмы" предназначен для обсуждения вопросов, связанных только с алгоритмами и структурами данных, без привязки к конкретному языку программирования и/или программному продукту.


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, maxim1000.

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Алгоритмы | Следующая тема »


 




[ Время генерации скрипта: 0.1353 ]   [ Использовано запросов: 20 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.