Этот пример иллюстрирует формирование луча микрофонной матрицы для выделения требуемых речевых сигналов в среде с преобладанием помех и шума. Такие операции полезны для улучшения качества речевого сигнала для восприятия или дальнейшей обработки. Например, шумной средой может быть торговый зал, а микрофонная решетка может быть установлена на мониторе торгового компьютера. Если торговый компьютер должен принимать речевые команды от трейдера, операция формирователя луча имеет решающее значение для повышения качества принимаемой речи и достижения заданной точности распознавания речи.
В этом примере показаны два типа формирователей луча во временной области: формирователь луча временной задержки и формирователь луча Frost. Он иллюстрирует, как можно использовать диагональную нагрузку для улучшения надежности формирователя луча Мороза. Речевые сигналы можно прослушивать на каждом этапе обработки, если система имеет звуковую поддержку.
Сначала мы определяем однородную линейную матрицу (ULA) для приема сигнала. Матрица содержит 10 ненаправленных микрофонов, а расстояние между элементами составляет 5 см.
microphone = ... phased.OmnidirectionalMicrophoneElement('FrequencyRange',[20 20e3]); Nele = 10; ula = phased.ULA(Nele,0.05,'Element',microphone); c = 340; % sound speed, in m/s
Затем мы моделируем многоканальные сигналы, принимаемые матрицей микрофонов. Начнем с загрузки двух записанных речей и одной записи смеха. Мы также загружаем звуковой сегмент смеха как помехи. Частота дискретизации звуковых сигналов составляет 8 кГц.
Поскольку аудиосигнал обычно большой, считывать весь сигнал в память часто нецелесообразно. Поэтому в этом примере мы будем моделировать и обрабатывать сигнал потоковым способом, то есть разбивать сигнал на небольшие блоки на входе, обрабатывать каждый блок и затем собирать их на выходе.
Направление падения первого речевого сигнала составляет -30 градусов по азимуту и 0 градусов по возвышению. Направление второго речевого сигнала -10 градусов по азимуту и 10 градусов по возвышению. Пересечение происходит от 20 градусов по азимуту и 0 градусов по отметке.
ang_dft = [-30; 0]; ang_cleanspeech = [-10; 10]; ang_laughter = [20; 0];
Теперь мы можем использовать широкополосный коллектор для моделирования 3-секундного многоканального сигнала, принимаемого массивом. Обратите внимание, что этот подход предполагает, что каждый входной одноканальный сигнал принимается в начале массива одним микрофоном.
fs = 8000; collector = phased.WidebandCollector('Sensor',ula,'PropagationSpeed',c,... 'SampleRate',fs,'NumSubbands',1000,'ModulatedInput', false); t_duration = 3; % 3 seconds t = 0:1/fs:t_duration-1/fs;
Мы генерируем сигнал белого шума мощностью 1e-4 Вт, чтобы представить тепловой шум для каждого датчика. Локальный поток случайных чисел обеспечивает воспроизводимые результаты.
prevS = rng(2008);
noisePwr = 1e-4; % noise powerТеперь мы начинаем моделирование. На выходе принятый сигнал запоминается в 10-столбцовой матрице. Каждый столбец матрицы представляет сигнал, собранный одним микрофоном. Обратите внимание, что во время моделирования мы также воспроизводим звук с использованием метода потоковой передачи.
% preallocate NSampPerFrame = 1000; NTSample = t_duration*fs; sigArray = zeros(NTSample,Nele); voice_dft = zeros(NTSample,1); voice_cleanspeech = zeros(NTSample,1); voice_laugh = zeros(NTSample,1); % set up audio device writer audioWriter = audioDeviceWriter('SampleRate',fs, ... 'SupportVariableSizeInput', true); isAudioSupported = (length(getAudioDevices(audioWriter))>1); dftFileReader = dsp.AudioFileReader('dft_voice_8kHz.wav',... 'SamplesPerFrame',NSampPerFrame); speechFileReader = dsp.AudioFileReader('cleanspeech_voice_8kHz.wav',... 'SamplesPerFrame',NSampPerFrame); laughterFileReader = dsp.AudioFileReader('laughter_8kHz.wav',... 'SamplesPerFrame',NSampPerFrame); % simulate for m = 1:NSampPerFrame:NTSample sig_idx = m:m+NSampPerFrame-1; x1 = dftFileReader(); x2 = speechFileReader(); x3 = 2*laughterFileReader(); temp = collector([x1 x2 x3],... [ang_dft ang_cleanspeech ang_laughter]) + ... sqrt(noisePwr)*randn(NSampPerFrame,Nele); if isAudioSupported play(audioWriter,0.5*temp(:,3)); end sigArray(sig_idx,:) = temp; voice_dft(sig_idx) = x1; voice_cleanspeech(sig_idx) = x2; voice_laugh(sig_idx) = x3; end
Заметьте, что смех маскирует речевые сигналы, делая их невразумительными. Мы можем построить график сигнала в канале 3 следующим образом:
plot(t,sigArray(:,3)); xlabel('Time (sec)'); ylabel ('Amplitude (V)'); title('Signal Received at Channel 3'); ylim([-3 3]);

Формирователь луча временной задержки компенсирует разности времени прихода по матрице для сигнала, поступающего из конкретного направления. Синхронизированные по времени многоканальные сигналы когерентно усредняются для улучшения отношения сигнал/шум (SNR). Теперь определите угол управления, соответствующий направлению падения первого речевого сигнала, и создайте формирователь луча временной задержки.
angSteer = ang_dft; beamformer = phased.TimeDelayBeamformer('SensorArray',ula,... 'SampleRate',fs,'Direction',angSteer,'PropagationSpeed',c)
beamformer =
phased.TimeDelayBeamformer with properties:
SensorArray: [1x1 phased.ULA]
PropagationSpeed: 340
SampleRate: 8000
DirectionSource: 'Property'
Direction: [2x1 double]
WeightsOutputPort: false
Затем мы обрабатываем синтезированный сигнал, строим график и слушаем выходной сигнал обычного формирователя луча. Опять же, мы воспроизводим звуковой сигнал в виде луча во время обработки.
signalsource = dsp.SignalSource('Signal',sigArray,... 'SamplesPerFrame',NSampPerFrame); cbfOut = zeros(NTSample,1); for m = 1:NSampPerFrame:NTSample temp = beamformer(signalsource()); if isAudioSupported play(audioWriter,temp); end cbfOut(m:m+NSampPerFrame-1,:) = temp; end plot(t,cbfOut); xlabel('Time (Sec)'); ylabel ('Amplitude (V)'); title('Time Delay Beamformer Output'); ylim([-3 3]);

Можно измерить усиление речи по коэффициенту усиления матрицы, который представляет собой отношение выходного сигнала к помехе плюс шум (SINR) к входному SINR.
agCbf = pow2db(mean((voice_cleanspeech+voice_laugh).^2+noisePwr)/...
mean((cbfOut - voice_dft).^2))agCbf = 9.5022
Первый речевой сигнал начинает появляться на выходе формирователя луча временной задержки. Мы получаем улучшение SINR 9,4 дБ. Однако фоновый смех все равно сравним с речью. Чтобы получить лучшую производительность формирователя луча, используйте формирователь луча Frost.
За счет прикрепления фильтров FIR к каждому датчику формирователь луча Frost имеет больше весов для формирования луча для подавления помех. Это адаптивный алгоритм, который размещает нули в изученных направлениях помех, чтобы лучше подавить помехи. В рулевом направлении формирователь луча Frost использует ограничения без искажений, чтобы гарантировать, что желаемые сигналы не подавляются. Создадим формирователь луча Frost с 20-краевым FIR после каждого датчика.
frostbeamformer = ... phased.FrostBeamformer('SensorArray',ula,'SampleRate',fs,... 'PropagationSpeed',c,'FilterLength',20,'DirectionSource','Input port');
Затем обработайте синтезированный сигнал с помощью формирователя луча Фроста.
reset(signalsource); FrostOut = zeros(NTSample,1); for m = 1:NSampPerFrame:NTSample FrostOut(m:m+NSampPerFrame-1,:) = ... frostbeamformer(signalsource(),ang_dft); end
Мы можем воспроизвести и построить график всего аудиосигнала, как только он будет обработан.
if isAudioSupported play(audioWriter,FrostOut); end plot(t,FrostOut); xlabel('Time (sec)'); ylabel ('Amplitude (V)'); title('Frost Beamformer Output'); ylim([-3 3]);

% Calculate the array gain agFrost = pow2db(mean((voice_cleanspeech+voice_laugh).^2+noisePwr)/... mean((FrostOut - voice_dft).^2))
agFrost = 14.4385
Обратите внимание, что пересечение теперь отменено. Формирователь луча Frost имеет коэффициент усиления матрицы 14 дБ, что на 4,5 дБ выше коэффициента усиления формирователя луча временной задержки. Улучшение производительности впечатляет, но имеет высокую вычислительную стоимость. В предыдущем примере для каждого микрофона используется фильтр КИХ порядка 20. Со всеми 10 датчиками необходимо инвертировать матрицу 200 на 200, что может быть дорого при обработке в реальном времени.
Далее мы хотим направить массив в направлении второго речевого сигнала. Предположим, что мы не знаем точного направления второго речевого сигнала, за исключением грубой оценки азимута -5 градусов и отметки 5 градусов.
release(frostbeamformer); ang_cleanspeech_est = [-5; 5]; % Estimated steering direction reset(signalsource); FrostOut2 = zeros(NTSample,1); for m = 1:NSampPerFrame:NTSample FrostOut2(m:m+NSampPerFrame-1,:) = frostbeamformer(signalsource(),... ang_cleanspeech_est); end if isAudioSupported play(audioWriter,FrostOut2); end plot(t,FrostOut2); xlabel('Time (sec)'); ylabel ('Amplitude (V)'); title('Frost Beamformer Output'); ylim([-3 3]);

% Calculate the array gain agFrost2 = pow2db(mean((voice_dft+voice_laugh).^2+noisePwr)/... mean((FrostOut2 - voice_cleanspeech).^2))
agFrost2 = 6.1927
Речь едва слышна. Несмотря на усиление 6,1 дБ от формирователя луча, производительность страдает от неточного направления рулевого управления. Одним из способов повышения надежности формирователя луча Frost является использование диагональной нагрузки. Этот подход добавляет небольшую величину к диагональным элементам матрицы оцененной ковариации. Здесь используется диагональное значение 1e-3.
% Specify diagonal loading value release(frostbeamformer); frostbeamformer.DiagonalLoadingFactor = 1e-3; reset(signalsource); FrostOut2_dl = zeros(NTSample,1); for m = 1:NSampPerFrame:NTSample FrostOut2_dl(m:m+NSampPerFrame-1,:) = ... frostbeamformer(signalsource(),ang_cleanspeech_est); end if isAudioSupported play(audioWriter,FrostOut2_dl); end plot(t,FrostOut2_dl); xlabel('Time (sec)'); ylabel ('Amplitude (V)'); title('Frost Beamformer Output'); ylim([-3 3]);

% Calculate the array gain agFrost2_dl = pow2db(mean((voice_dft+voice_laugh).^2+noisePwr)/... mean((FrostOut2_dl - voice_cleanspeech).^2))
agFrost2_dl = 6.4788
Теперь выходной речевой сигнал улучшается, и мы получаем улучшение усиления 0,3 дБ из метода диагональной нагрузки.
release(frostbeamformer); release(signalsource); if isAudioSupported pause(3); % flush out AudioPlayer buffer release(audioWriter); end rng(prevS);
В этом примере показано, как использовать формирователи луча во временной области для извлечения речевых сигналов из измерений в матрице шумных микрофонов. Пример также показывает, как имитировать сигнал, доминирующий в помехах, принимаемый матрицей микрофонов. В примере использовались как временная задержка, так и формирователи луча Frost и сравнивались их характеристики. Формирователь луча Мороза имеет лучшую возможность подавления помех. Пример также иллюстрирует использование диагональной нагрузки для улучшения надежности формирователя луча Мороза.
[1] О. Л. Фрост III, Алгоритм линейной адаптивной обработки массива с ограничением, Proceedings of the IEEE, Vol. 60, Number 8, Aug. 1972, pp. 925-935.