語音PCM
脈沖編碼調制(Pulse Code Modulation, PCM)是語音信號的重要編碼方式之一。語音編碼是將模擬信號轉為數字信號的語音通信技術,分為波形編碼、參量編碼和混合編碼等類型。波形編碼針對語音波形進行,在降低量化樣本比特數的同時保持了良好的語音質量。
PCM編碼就是一種波形編碼方法,通過每隔一段時間對模擬語音信號采樣,將其取整量化,用二進制碼表示抽樣量化的幅值,實現將語音數字化的編碼調制。
PCM是現代數字傳輸系統普遍采用的調制方式。PCM可以向用戶提供多種業務,包括2M~155 Mbit/s速率的數字數據專線業務和語音、圖像、遠程教學等業務,適用於傳輸速率要求高、需要更高帶寬的應用,在語音信號處理中有着廣泛的運用。
PCM分為抽樣、量化和編碼三個步驟,如下圖所示。下面對此過程進行介紹
1.抽樣
語音信號具有頻率和振幅特征,頻率對應於時間軸,振幅對應於電平軸,而由於存儲空間有限,數字編碼過程中,必須對正弦信號進行抽樣。抽樣是把模擬信號以其信號帶寬2倍以上的頻率提取樣值,變為在時間軸上離散的抽樣信號的過程。對一個正弦信號進行抽樣獲得的抽樣信號是一個脈沖幅度調制信號,對抽樣信號進行檢波和平滑濾波,即可還原出原來的模擬信號。
抽樣過程就是抽取某點的頻率值的過程。顯然,在1s內抽取的點越多,獲取的頻率信息越豐富。為了復原波形,一次振動中必須有2個點的采樣,人耳能夠感覺到的最高頻率為20kHz,因此要滿足人耳的聽覺要求,則需要至少每秒進行40000次采樣,即采樣率為44. 1 kHz。光有頻率信息是不夠的,還必須獲得該頻率的能量值並量化,用於表示信號強度。量化電平數為2的整數次冪,常用16 bit的采樣大小即26。例如對一個語音信號進行8次采樣,采樣點分別對應的能量值分別為Al~A8,使用2bit的采樣大小只能保留Al ~A8中4個點,而進行3bit的采樣則剛好記錄下8點的所有信息。采樣率和采樣大小的值越大,記錄的波形越接近原始信號。
抽樣可以看作是周期性單位沖激脈沖和語音模擬信號的相乘,結果為一系列的周期性沖激脈沖,脈沖的高度與模擬信號的取值成正比。若抽樣速率足夠大,則離散的沖激脈沖可以完全代替模擬信號,即由這些離散信號可恢復出原信號。
抽樣定理表述為:設有最高頻率小於\(f_h\)的信號\(m(t)\),將周期為\(T\le 1/(2f_h)\)的沖激脈沖信號\(\delta_T(t)\)與其相乘進行抽樣,則\(m(t)\)被抽樣信號完全確定。
則\(m(t)\)的傅里葉變換:
其中,
由上可見,當頻率間隔\(f_s\ge 2f_H\)時, \(M_s(f)\)包含的每個原信號頻譜間不重疊,這樣就能用低通濾波器從抽樣信號中恢復原信號。
由於實際的濾波器不夠理想,邊緣不夠陡峭,因此實際抽樣頻率需要比\(2f_H\)大些,如典型的電話信號最高頻率限制在3400 Hz,而抽樣頻率一般取為8kHz
2.量化
抽樣信號雖然是時間軸上離散的信號,但仍是模擬信號,其值在一定的取值范圍內可有無限多個值。顯然,對無限個樣值給出數字碼組來對應是不可能的。為了實現以數字碼表示樣值,必須采用四舍五入的方法把樣值分級取整,使一定取值范圍內的樣值由無限多個值變為有限個值。這一過程稱為量化。
量化后的抽樣信號與量化前相比較有所失真,且不再是模擬信號。這種量化失真在接收端還原模擬信號時表現為噪聲,稱為量化噪聲。量化噪聲的大小取決於把樣值分級取整的方式,分的級數越多,即量化級差或間隔越小,量化噪聲也越小。
設模擬抽樣信號為\(m(kT)\) ,抽樣值仍為取值連續的變量。用\(N\)個不同的二進制數字碼元來表示抽樣值大小,則共有\(M=2^N\)個不同的抽樣值。
將抽樣范圍划分為\(M\)個區間,每個區間用一個電平表示。這樣,共有\(M\)個離散電平,成為量化電平。M個抽樣區間等間隔划分,為均勻量化,否則為非均勻量化。量化信號表示為:
若為均勻量化,量化值可取量化間隔的中點:
3.編碼
量化后的抽樣信號在一定范圍內僅有有限個可取的樣值,且信號正負幅度分布的對稱性使正負樣值個數相等,正負向的量化級對稱分布。若將有限個量化樣值絕對值從小到大排列,依次賦予十進制數字,以\(+\)、\(-\)號為前綴,則量化后的抽樣信號就轉化為按時序排列的十進制數字碼流。將數字轉換為二進制編碼,根據十進制代碼總個數確定二進制位數,即字長。這樣把量化的抽樣信號變換成給定字長的二進制碼流的過程稱為編碼。
二進制碼可經受較高的噪聲電平的干擾,並且易於再生,因此PCM一般采用二進制碼。
對於\(Q\)個量化電平,可以用\(k\)位二進制碼表示,其中每一種組合為一個碼字。在點對點通信或短距離通信中,采用\(k=7\)位碼已基本滿足質量要求,而對於干線遠程的全網通信,一般需要經過多次轉接,有較高的質量要求,目前多采用8位編碼PCM設備。
量化及代碼
語音信號的特點就是小信號較重要,需要提高小信號的量化信噪比。所以需要對信號進行非線性壓縮,改變大信號與小信號比例關系。
此時,\(c_i\)就是[1/128,1/64,1/32,1/16,...,1/2]每段間隔都有一個重建值\(\hat{s}^{'}\)。
正負(1bit)段落碼(3bit)段內電平碼(4bit)
比如:輸入x (-4096<x<4096)
正負(1bit):
大於零,1;小於零,0;
%實驗要求一:PCM編解碼實驗
clear all;
close all;
[x fs ]= audioread('C6_1_y.wav');
v=1;
xx=x/v;
sxx=floor(xx*4096);
y=pcm_encode(sxx);
yy=pcm_decode(y,v)';
nq=sum((x-yy).*(x-yy))/length(x);
sq=mean(yy.^2);
snr=(sq/nq);
t=(1:length(x))/fs;
subplot(211)
plot(t,x/max(abs(x)))
axis tight
title('(a)編碼前語音')
xlabel('時間/s')
ylabel('幅度')
subplot(212)
plot(t,yy/max(abs(yy)))
axis tight
title('(b)解碼后語音')
xlabel('時間/s')
ylabel('幅度')
snrq=10*log10(mean(snr))
figure;
plot(t,abs(x-yy));
title('編碼前后誤差')
encoder
%PCM編碼函數
function[out]=pcm_encode(x)
n=length(x); %-4096<x<4096
for i=1:n
if x(i)>0
out(i,1)=1; %根據符號輸出第1位量化結果
else
out(i,1)=0;
end
if abs(x(i))>=0 & abs(x(i))<32 %根據輸入范圍輸出后2-4位
out(i,2)=0; out(i,3)=0; out(i,4)=0; step=2;st=0;
elseif 32<=abs(x(i)) & abs(x(i))<64
out(i,2)=0; out(i,3)=0; out(i,4)=1; step=2;st=32;
elseif 64<=abs(x(i)) & abs(x(i))<128
out(i,2)=0; out(i,3)=1; out(i,4)=0; step=4;st=64;
elseif 128<=abs(x(i)) & abs(x(i))<256
out(i,2)=0; out(i,3)=1; out(i,4)=1; step=8;st=128;
elseif 256<=abs(x(i)) & abs(x(i))<512
out(i,2)=1; out(i,3)=0; out(i,4)=0; step=16;st=256;
elseif 512<=abs(x(i)) & abs(x(i))<1024
out(i,2)=1; out(i,3)=0; out(i,4)=1; step=32;st=512;
elseif 1024<=abs(x(i)) & abs(x(i))<2048
out(i,2)=1; out(i,3)=1; out(i,4)=0; step=64;st=1024;
elseif 2048<=abs(x(i)) & abs(x(i))<4096
out(i,2)=1; out(i,3)=1; out(i,4)=1; step=128;st=2048;
else
out(i,2)=1; out(i,3)=1; out(i,4)=1; step=128;st=2048;
end
if(abs(x(i))>=4096) %超出最大幅值的量化結果
out(i,2:8)=[1 1 1 1 1 1 1];
else %未超出,計算后四位
tmp=floor((abs(x(i))-st)/step);
t=dec2bin(tmp,4)-48; %十進制轉為4位二進制字符串
out(i,5:8)=t(1:4);
end
end
out=reshape(out',1,8*n); %調整為長為8n的行向量
decoder
%PCM解碼函數
function[out]=pcm_decode(ins,v)
n=length(ins); %輸入為8位PCM采樣信號
in=reshape(ins',8,n/8)'; %調整矩陣行列數
slot(1)=0; %量化幅值
slot(2)=32;
slot(3)=64;
slot(4)=128;
slot(5)=256;
slot(6)=512;
slot(7)=1024;
slot(8)=2048;
step(1)=2; %步長
step(2)=2;
step(3)=4;
step(4)=8;
step(5)=16;
step(6)=32;
step(7)=64;
step(8)=128;
for i=1:n/8
ss=2*in(i,1)-1; %解碼符號位
tmp=in(i,2)*4+in(i,3)*2+in(i,4)+1; %解碼2-4位
st=slot(tmp);
dt=(in(i,5)*8+in(i,6)*4+in(i,7)*2+in(i,8))*step(tmp)+0.5*step(tmp); %解碼5-8位
out(i)=ss*(st+dt)/4096*v; %解碼結果相加,乘以量化電平
end
Reference:梁瑞宇等. 語音信號處理實驗教程[M]. 北京: 機械工業出版社, 2016.2.