【语音去噪】基于matlab低通滤波器语音去噪【含Matlab源码 1900期】

一、语音处理简介

1 语音信号的特点
通过对大量语音信号的观察和分析发现,语音信号主要有下面两个特点:
①在频域内,语音信号的频谱分量主要集中在300~3400Hz的范围内。利用这个特点,可以用一个防混迭的带通滤波器将此范围内的语音信号频率分量取出,然后按8kHz的采样率对语音信号进行采样,就可以得到离散的语音信号。
②在时域内,语音信号具有“短时性”的特点,即在总体上,语音信号的特征是随着时间而变化的,但在一段较短的时间间隔内,语音信号保持平稳。在浊音段表现出周期信号的特征,在清音段表现出随机噪声的特征。

2 语音信号的采集
在将语音信号进行数字化前,必须先进行防混叠预滤波,预滤波的目的有两个:①抑制输入信导各领域分量中频率超出fs/2的所有分量(fs为采样频率),以防止混叠干扰。②抑制50Hz的电源工频干扰。这样,预滤波器必须是一个带通滤波器,设其上、下截止颜率分别是fH和fL,则对于绝人多数语音编译码器,fH=3400Hz、fL=60~100Hz、采样率为fs=8kHz;而对丁语音识别而言,当用于电话用户时,指标与语音编译码器相同。当使用要求较高或很高的场合时fH=4500Hz或8000Hz、fL=60Hz、fs=10kHz或20kHz。
为了将原始模拟语音信号变为数字信号,必须经过采样和量化两个步骤,从而得到时间和幅度上均为离散的数字语音信号。采样也称抽样,是信号在时间上的离散化,即按照一定时间间隔△t在模拟信号x(t)上逐点采取其瞬时值。采样时必须要注意满足奈奎斯特定理,即采样频率fs必须以高于受测信号的最高频率两倍以上的速度进行取样,才能正确地重建波它是通过采样脉冲和模拟信号相乘来实现的。
在采样的过程中应注意采样间隔的选择和信号混淆:对模拟信号采样首先要确定采样间隔。如何合理选择△t涉及到许多需要考虑的技术因素。一般而言,采样频率越高,采样点数就越密,所得离散信号就越逼近于原信号。但过高的采样频率并不可取,对固定长度(T)的信号,采集到过大的数据量(N=T/△t),给计算机增加不必要的计算工作量和存储空间;若数据量(N)限定,则采样时间过短,会导致一些数据信息被排斥在外。采样频率过低,采样点间隔过远,则离散信号不足以反映原有信号波形特征,无法使信号复原,造成信号混淆。根据采样定理,当采样频率大于信号的两倍带宽时,采样过程不会丢失信息,利用理想滤波器可从采样信号中不失真地重构原始信号波形。量化是对幅值进行离散化,即将振动幅值用二进制量化电平来表示。量化电平按级数变化,实际的振动值是连续的物理量。具体振值用舍入法归到靠近的量化电平上。
语音信号经过预滤波和采样后,由A/D变换器变换为二址制数字码。这种防混叠滤波通常与模数转换器做在一个集成块内,因此目前来说,语音信号的数字化的质量还是有保证的。
采集到语音信号之后,需要对语音信号进行分析,如语音信号的时域分析、频谱分析、语谱图分析以及加噪滤波等处理。

3 语音信号分析技术
语音信号分析是语音信号处理的前提和基础,只有分析出可表示语音信号本质特征的参数,才有可能利用这些参数进行高效的语音通信、语音合成和语音识别等处理[8]。而且,语音合成的音质好坏,语音识别率的高低,也都取决于对语音信号分桥的准确性和精确性。因此语音信号分析在语音信号处理应用中具有举足轻重的地位。
贯穿于语音分析全过程的是“短时分析技术”。因为,语音信号从整体来看其特性及表征其本质特征的参数均是随时间而变化的,所以它是一个非乎稳态过程,不能用处理乎稳信号的数字信号处理技术对其进行分析处理。但是,由于不同的语音是由人的口腔肌肉运动构成声道某种形状而产生的响应,而这种口腔肌肉运动相对于语音频率来说是非常缓慢的,所以从另一方面看,虽然语音倍号具有时变特性,但是在一个短时间范围内(一般认为在10~30ms的短时间内),其特性基本保持不变即相对稳定,因面可以将其看作是一个准稳态过程,即语音信号具有短时平稳性。所以任何语音信号的分析和处理必须建立在“短时”的基础上.即进行“短时分析”,将语音信号分为一段一段来分析其特征参数,其中每一段称为一“帧”,帧长一般取为10~30ms。这样,对于整体的语音信号来讲,分析出的是由每一帧特征参数组成的特征参数时间序列。
根据所分析出的参数的性质的不同,可将语音信号分析分为时域分析、频域分析、倒领域分析等;时域分析方法具有简单、计算量小、物理意义明确等优点,但由于语音信号最重要的感知特性反映在功率谱中,而相位变化只起着很小的作用,所以相对于时域分析来说频域分析更为重要。

4 语音信号的时域分析
语音信号的时域分析就是分析和提取语音信号的时域参数。进行语音分析时,最先接触到并且也是最直观的是它的时域波形。语音信号本身就是时域信号,因而时域分析是最早使用,也是应用最广泛的一种分析方法,这种方法直接利用语音信号的时域波形。时域分析通常用于最基本的参数分析及应用,如语音的分割、预处理、大分类等。这种分析方法的特点是:①表示语音信号比较直观、物理意义明确。②实现起来比较简单、运算且少。③可以得到语音的一些重要的参数。④只使用示波器等通用设备,使用较为简单等。
语音信号的时域参数有短时能量、短时过零率、短时白相关函数和短时平均幅度差函数等,这是语音信号的一组最基本的短时参数,在各种语音信号数字处理技术中都要应用[6]。在计算这些参数时使用的一般是方窗或汉明窗。

5 语音信号的频域分析
语音信号的频域分析就是分析语音信号的频域持征。从广义上讲,语音信号的频域分析包括语音信号的频谱、功率谱、倒频谱、频谱包络分析等,而常用的频域分析方法有带通滤波器组法、傅里叶变换法、线件预测法等几种。

二、部分源代码

clear;
close all;
clc;
%% 把原音频得到的矩阵数据作为模拟信号
load xinghai.mat %加载在Matlab中为data变量
%% 一、采样(Sampling)
Fs=44100;%采用CD音质的抽样率44100,
audiowrite('xinghai.flac',data,Fs);% 双声道无损音频.flac文件
%% 控制变量区
RateL=[];
RateR=[];
SNRcount=[];
SNR=[19,17,15,12,9,6,3,0,-3,-6];% 所掺杂加性白噪声的信噪比大小(分贝)
for n=1:1:length(SNR)
%% 1)读文件
samples=[1+5*(n-1)*Fs,5*n*Fs];%读取前5秒数据
clear Fs;
[Data,Fs]=audioread('xinghai.flac',samples); 
MusicLeft=Data(:,1);  % 左声道
MusciRight=Data(:,2); % 右声道
% time=(1/Fs)*length(Data);%查看歌曲总时长
% soundsc(MusciRight,Fs);%播放右声道
%% 2)时域图
N=length(Data);%信号的长度
t=(0:N-1)/Fs;%时域范围
figure(1);
set(gcf,'position',[200 480 530 300]);
subplot(211);
plot(t,Data); %音频信号时域图
title('采样后的初始音频时域图');xlabel('Time');ylabel('Amplitude');
legend('左声道','右声道');
%% 3)频谱图
position=fft(Data,N);
subplot(212);
df=Fs/length(Data); %计算谱线间隔
f=0:df:(Fs/2-df); %频谱范围,可只截取前半段(因为抽样频率高于最大频率的2倍)
Yf=abs(position); %幅度响应
Yf=Yf(1:length(Yf)/2); %由于幅度响应是偶函数,所以截取一半
plot(f,Yf); %音频信号频谱图
axis([0,Fs/10,0,300]);
title('采样后的初始音频频谱图');xlabel('f/Hz');ylabel('Amplitude');
pause(0.001);

%% 二、ADC-量化(Quantizing)
%% 1)左声道采用8位A律13折线法量化
sign_=sign(MusicLeft);%符号函数
MusicLeft=abs(MusicLeft); %取绝对值
maxs=max(MusicLeft);%解码时会用到
MusicLeft=MusicLeft/maxs;%归一化
MusicLeft=2048*MusicLeft;%[0,1]量化为[0,2048]
%% 2)右声道采用11位均匀量化法,一共12位,1位是符号位,11位是量化
R=zeros(2.^12); %储存矩阵(全零)
Max=max(MusciRight);% 找出波形最大值
Min=min(MusciRight);% 找出波形最小值
delv=(Max - Min)/2.^12;% 均匀量化的量化间隔
for g=1:2^12+1
    R(g)= Min+delv*(g - 1);%量化区间的端点
end
MusciRight_riser=MusciRight; % 向上取整法
for i=1:length(MusciRight)
    for j = 1:2^12
        if MusciRight_riser(i)>=R(j) && MusciRight_riser(i)<=R(j+1)
            MusciRight_riser(i)=(R(j)+R(j+1))/2;
            break
        end
    end
end
MusciRight_riser=fix((MusciRight_riser+1)*4096/2);%将交流信号叠加直流分量平移,把[-1,1]量化为[0,4096]
% MusciRight_tread=MusciRight;%% 向下取整法
% for i=1:length(MusciRight)
%     for j=1:2^11
%        if MusciRight_tread(i)>=(R(j)-1/2*delv) && MusciRight_tread(i)<=(R(j)+1/2*delv)
%          MusciRight_tread(i) = R(j);
%          break
%         end
%     end
% end
%% 3)量化后的时域图
N=length(Data);%信号的长度
t=(0:N-1)/Fs;%时域范围
figure(2);
set(gcf,'position',[750 480 530 300]);
subplot(211);
stairs(t,MusicLeft); %音频信号时域图
title('8位A律13折线法量化后的左声道音频时域图');xlabel('Time');ylabel('Amplitude');
% 画出原声波以及量化之后的声波
subplot(212);
stairs(t,MusciRight_riser);
title('11位均匀量化法量化后的右声道音频时域图');xlabel('Time');ylabel('Amplitude');
pause(0.001);

%% 三、编码(Encoding)
%% 1)左声道采用8位A律13折线法编码
encodeL=zeros(length(MusicLeft),8); %储存8位编码矩阵(全零)
%%%%%%%%%%%%%%%%%%%%%%参数矩阵%%%%%%%%%%%%%%%%%%%%%%%%%%%%
sp=[0,16,32,64,128,256,512,1024]; %段落起始值
spmin=[1,1,2,4,8,16,32,64]; %除以16,得到每段最小的量化间隔
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
for m=1:length(MusicLeft)
    %符号位判断
    if sign_(m)>=0 %符号为正,符号位为1
        encodeL(m,1)=1;
    else
        if sign_(m)<0 %符号为负,符号位为0
        encodeL(m,1)=0;
        end
    end
    %段落码判断
    if MusicLeft(m)>128 && MusicLeft(m)<2048 %在第五段与第八段之间,段落码第一位为1
    encodeL(m,2)=1;
    end
    if (MusicLeft(m)>32 && MusicLeft(m)<128)||(MusicLeft(m)>512 && MusicLeft(m)<2048)%在第三第四第七第八段内,段落码第二位为1
    encodeL(m,3)=1;
    end
    if (MusicLeft(m)>16 && MusicLeft(m)<32)||(MusicLeft(m)>64&&MusicLeft(m)<128)||(MusicLeft(m)>256&&MusicLeft(m)<512)||(MusicLeft(m)>1024 && MusicLeft(m)<2048)%在第二第四第六第八段内,段落码第三位为1
    encodeL(m,4)=1;
    end
    Paragraghindex=encodeL(m,2)*4+encodeL(m,3)*2+encodeL(m,4)+1; %找到位于第几段
    %段内码判断
    position=floor((MusicLeft(m)-sp(Paragraghindex))/spmin(Paragraghindex)); %求出在段内的位置,floor负无穷大方向取整
    if position==0
    encodeL(m,(5:8))=[0,0,0,0]; %输入为0,输出为0
    else
        k=num2str(dec2bin(position,4)); %段内码编码为二进制
        encodeL(m,5)=str2double(k(1));
        encodeL(m,6)=str2double(k(2));
        encodeL(m,7)=str2double(k(3));
        encodeL(m,8)=str2double(k(4));
    end
end
%% 2)右声道采用11位均匀量化法编码
encodeR=zeros(length(MusciRight_riser),12);
for u=1:length(MusciRight_riser)
    h=num2str(dec2bin(MusciRight_riser(u),12)); %段内码编码为二进制
        encodeR(u,1)=str2double(h(1));
        encodeR(u,2)=str2double(h(2));
        encodeR(u,3)=str2double(h(3));
        encodeR(u,4)=str2double(h(4));
        encodeR(u,5)=str2double(h(5));
        encodeR(u,6)=str2double(h(6));
        encodeR(u,7)=str2double(h(7));
        encodeR(u,8)=str2double(h(8));
        encodeR(u,9)=str2double(h(9));
        encodeR(u,10)=str2double(h(10));
        encodeR(u,11)=str2double(h(11));
        encodeR(u,12)=str2double(h(12));
end
%% 3)转串行
SequenceL = reshape(encodeL,1,[]);%重构数组为1*n的序列sequence,便于串行发送
SequenceR = reshape(encodeR,1,[]);%重构数组为1*n的序列sequence,便于串行发送
%% 数字信号的2ASK调制
% f=8000; % 正弦载波信号的频率
% A=1; % 载波的幅度
% % Q=f/F; % 频率比 ,即一个码元宽度中的正弦周期个数,为适配下面滤波器参数选取,推荐将 Q 设为Q>=1/3
% M=500; % 一个正弦周期内的采样点数
% t=(0:M-1)/M/f; % 一个正弦信号周期内的时间
% carry=A*sin(2*pi*f*t); % 一个码元宽度内的正弦载波信号
% st=sequence.*carry;
% plot(st);
% axis([60000 60200 -0.1 1.1]);

%% 四、发送端口
VoltageSequenceL=SequenceL*5.0;%以TTL电平发送
VoltageSequenceR=SequenceR*5.0;%以TTL电平发送
%% 五、加性高斯信道
NosiedB=SNR(n);
NoiseSequenceL=awgn(VoltageSequenceL,NosiedB,'measured');
NoiseSequenceR=awgn(VoltageSequenceR,NosiedB,'measured');
%% 加噪前后对比图
figure(3);
clf;
set(gcf,'position',[200 45 530 350]);
subplot(211);
hold on
stairs(VoltageSequenceL);
plot(NoiseSequenceL,'r');
axis([60000 60125 0 10]);
title('叠加高斯白噪声前后对比图');
legend('左声道数字信号','加噪后');
subplot(212);
hold on
stairs(VoltageSequenceR);
plot(NoiseSequenceR,'r');
axis([60000 60125 0 10]);
grid on;
hold off
legend('右声道数字信号','加噪后');
pause(0.001);
%% 眼图绘制(在Rate_SNRcurve.m做演示)
% for i=2:1:3000
%         plot(NoiseSequenceL(i:i+2));
%         pause(0.001);
%         hold on;  
% end

%% 六、接收端口
%% 1)以TTL电平的一半(2.5V)进行抽样判决
DeVoltageSequenceL=NoiseSequenceL>2.5;%因为是单极性波形
DeVoltageSequenceR=NoiseSequenceR>2.5;%因为是单极性波形
%% 2)转并行
DeSequenceL=reshape(DeVoltageSequenceL,length(DeVoltageSequenceL)/8,8);
DeSequenceR=reshape(DeVoltageSequenceR,length(DeVoltageSequenceR)/12,12);
%% 3)误码率随信噪比变化曲线(为优化运算速度,单独提取为Rate_SNRcurve.m做演示)
% 调用biterr函数法
% [number,ratio]=biterr(DeSequenceL,encodeL);
% 自写函数法
% ErrorbitnumL=sum(sum(decodeL~=encodeL));
% ErrorbitnumR=sum(sum(decodeR~=encodeR));
% [longL,wideL]=size(decodeL);
% [longR,wideR]=size(decodeR);
% ErrorbitRateL=ErrorbitnumL/(longL*wideL);
% ErrorbitRateR=ErrorbitnumR/(longR*wideR);
% RateL=[RateL,ErrorbitRateL]; %#ok<AGROW>
% RateR=[RateR,ErrorbitRateR]; %#ok<AGROW>
% SNRcount=[SNRcount,SNR(n)]; %#ok<AGROW>
% figure(6);
%  hold off
%  semilogy(SNRcount,RateL,'b*');
%  hold on
%  semilogy(SNRcount,RateR,'bo');

%% 七、译码(Decoding)
%% 1)左声道译码(A律13折线法)
decodeL=zeros(length(DeSequenceL),1); %储存解码矩阵(全零)
%%%%%%%%%%%%%%%%%%%%%%参数矩阵%%%%%%%%%%%%%%%%%%%%%%%%%%%%
sp=[0,16,32,64,128,256,512,1024]; %段落起始值
spmin=[1,1,2,4,8,16,32,64]; %除以16,得到每段的最小量化间隔
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
for s=1:length(DeSequenceL)
    %确定量化电压的正负
    if DeSequenceL(s,1)==1%符号位为1
        Polarity=1;   %解码符号为正
    else          %符号位为0
        Polarity=-1;  %解码符号为负
    end
    %确定所在的段落码
    Paragraghindex=DeSequenceL(s,2)*4+DeSequenceL(s,3)*2+DeSequenceL(s,4)+1;
    %确定在段内的位置
    position=bin2dec(num2str(DeSequenceL(s,(5:8))));
    %确定该量化电平值
    decodeL(s,1)=Polarity*(sp(Paragraghindex)+spmin(Paragraghindex)*(position+0.5));%+0.5将码组放在量化间隔中间。
end
%% 2)右声道译码(11位均匀量化法)
decodeR=zeros(length(DeSequenceR),1); %储存解码矩阵(全零)
for f=1:length(DeSequenceR)
    decodeR(f)=bin2dec(num2str(DeSequenceR(f,(1:12))));
end

%% 八、DAC生成交流信号
%% 1)左声道
decodeL=decodeL/2048;%归一化电压
MusicoutL=decodeL*maxs;%恢复到原来的幅度
%% 2)右声道
MusicoutR=(decodeR/4096.0)*2-1;%恢复到原来的幅度,并滤去直流分量
%% 3)译码-DAC后的信号图
% N=length(Data);%信号的长度
% t=(0:N-1)/Fs;%时域范围
% figure(5);
% set(gcf,'position',[750 45 530 350]);
% subplot(211);
% plot(t,MusicoutL); %音频信号时域图
% title('译码-DAC后左声道输出音频时域图');xlabel('Time');ylabel('Amplitude');
% subplot(212);
% plot(t,MusicoutR); %音频信号时域图
% title('译码-DAC后右声道输出音频时域图');xlabel('Time');ylabel('Amplitude');
%%
% soundsc(Musicout,Fs);%播放输出音乐
%% 九、低通滤波器
%  y[n] = 2.2188y[n-1] - 3.0019y[n-2] + 2.4511y[n-3] - 1.2330y[n-4] + 0.3109y[n-5] + 0.0079 (  x[n] + 5x[n-1] + 10x[n-2] + 10x[n-3] + 5x[n-4] + x[n-5] );
%  B = 0.0079 * [ 1, 5, 10, 5, 1]; % 分子系数
%  A = [ 1, -2.2188, 3.0019, -2.4511, 1.2330, -0.3109]; % 分母系数
MusicfilteroutL = filter( 0.0079*[ 1, 5, 10, 5, 1], [1, -2.2188, 3.0019, -2.4511, 1.2330, -0.3109], MusicoutL );
MusicfilteroutR = filter( 0.0079*[ 1, 5, 10, 5, 1], [1, -2.2188, 3.0019, -2.4511, 1.2330, -0.3109], MusicoutR );
figure(4);
set(gcf,'position',[750 45 530 350]);
subplot(211);
plot(t,MusicfilteroutL); %音频信号时域图
title('低通滤波后左声道输出音频时域图');xlabel('Time');ylabel('Amplitude');
subplot(212);
plot(t,MusicfilteroutR); %音频信号时域图
title('低通滤波后右声道输出音频时域图');xlabel('Time');ylabel('Amplitude');
pause(0.25);
%% 十、输出
nameL=char('xinghai '+NosiedB+'dB'+' left_channel'+'.wav');
nameR=char('xinghai '+NosiedB+'dB'+' right_channel'+'.wav');
audiowrite(nameL,MusicfilteroutL,Fs);
audiowrite(nameR,MusicfilteroutR,Fs);
end

三、运行结果

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

四、matlab版本及参考文献

1 matlab版本
2014a

2 参考文献
[1]韩纪庆,张磊,郑铁然.语音信号处理(第3版)[M].清华大学出版社,2019.
[2]柳若边.深度学习:语音识别技术实践[M].清华大学出版社,2019.
[3]宋云飞,姜占才,魏中华.基于MATLAB GUI的语音处理界面设计[J].科技信息. 2013,(02)

猜你喜欢

转载自blog.csdn.net/TIQCmatlab/article/details/125363550