参考文章:
OFDM的基本原理剖析
基于matlab的ofdm系统设计与仿真
…
写程序前一定要理清原理思路,网上可参考资料很多,要综合学习,吸收所需。
根据上边参考的原理框图做基础仿真:
参数设定→子载波调制(QPSK)→串并变换→IFFT(调制)→+并串变换→+awgn→串并变换→-cp→FFT(解调)→并串变换→QPSK解调→误码率计算→绘制图形
%% 参数设置
close all;clc;
N=64; %IFFT数=子载波数(本例中) N个并行的符号
M=5000; %符号数
l_cp=N/4; %保护间隔长度
SNR=1:20; %仿真信噪比
snr=10.^(SNR/10); %将信噪比转化成直角坐标
BER_S=zeros(1,length(SNR)); %误码率
%% 随机信号生成
a=randi([0,1],1,N*M*2);
% t=1:length(a); size(a)
% plot(t,a,'.-r') grid on
%% QPSK调制
a2= reshape(a,log2(4),[])'; %以每组2比特进行分组,M=4★
a10= bi2de(a2); %二进制转化为十进制
y_psk=pskmod(a10,4,pi/4); %qpsk调制,初始相位pi/4 size(y_psk)
%% ifft、+cp
y0=reshape(y_psk,N,[]); %串并转换
y1=ifft(y0)*sqrt(N); %IFFT调制
y3=[y1(N-l_cp+1:end,:);y1]; %添加循环前缀(cp)
y_c=reshape(y3,[],1); %并串变换
[m,n]=size(y_c);
%% 经过AWGN信道
for i=1:length(SNR)
N0=1/2/snr(i); %计算噪声功率
N0_dB=10*log10(N0); %将噪声功率转换为dBW
ni=wgn(m,n,N0_dB); %产生高斯噪声
y_n=y_c+ni; %加噪
%% -cp、fft
y4=reshape(y_n,N+l_cp,[]); %串并变换
y5=y4(l_cp+1:end,:); %去cp
y6 = fft(y5)/sqrt(N); %fft
%% QPSK解调
y7=reshape(y6,[],1); %并串变换
yj=pskdemod(y7,4,pi/4); %qpsk解调
De_data1 = reshape(yj,[],1);
De_data2 = de2bi(De_data1);
q=reshape(De_data2',1,[]); %转换同输入a形式,便于误码率计算
%% 计算误码个数及误码率
q;
[number1,BER_S(i)] = symerr(a,q); %计算错误比特数和误码率== bit_A=length(find(a~=q))%统计错误比特数 p=number1/N;
end
BER_S
%% 绘制图形
figure;
semilogy(SNR,BER_S,'-k*');hold on;
axis([-1,15,10^-4,1]);
title('OFDM误码性能分析');
xlabel('信噪比SNR(dB)');ylabel('BER');
参数设定→子载波调制(QPSK)→串并变换→IFFT(调制)→+并串变换→多径信道→+awgn→串并变换→-cp→简单信道估计+均衡(包含FFT解调)→并串变换→QPSK解调→误码率计算→绘制图形
均衡1:对相位做简单补偿
均衡2:相当于ZF均衡
close all;clc;
%% 参数设置
SNR=1:20; %信噪比变化范围
snr=10.^(SNR/10); %将信噪比转化成直角坐标
M=64;%Nfft
N=500; %符号数
pathnum=4;
l_cp=pathnum+1; %保护间隔长度
BER_S=zeros(1,length(SNR)); %误码率
BER_Ss=zeros(1,length(SNR));%误码率
H=[];y6=[];y_dect=[];
w=zeros(2*M,N);
ws=zeros(2*M,N);
%% 初始序列生成qpsk调制
for ii=1:length(SNR)
a=randi([0 1],1,2*M*N);
a2= reshape(a,log2(4),[])';
a10= bi2de(a2);
xt=pskmod(a10,4,pi/4);
x=reshape(xt,M,N); %M×N
x1=zeros(M+l_cp,1);
x2=zeros(M,1);
for jj=1:N
h=(randn(pathnum,1)+1i*randn(pathnum,1))*sqrt(1/2/pathnum);%信道设置
x2=x(:,jj);
x2i=ifft(x2)*sqrt(M); %ifft
x1=[x2i(M-l_cp+1:M);x2i]; %+cp x1=[M+1×1]
%% 多径信道
y0=conv(x1,h); %y=x*h
y=y0(l_cp+1:l_cp+M,:); %-cp Y=[M×1]
%% awgn
[m,n]=size(y);
N0=1/2/snr(ii);
N0_dB=10*log10(N0);
ni=wgn(m,n,N0_dB);
ys=y+ni;
% 信道矩阵
H=zeros(M,M);
H1=zeros(M,1);
for kk=1:pathnum
H1(kk)=h(kk);
end
H(:,1)=H1; %第一列
for cc=1:M-1
H(:,cc+1)=circshift(H1,cc);
end %第一列依次循环移位置2→M-1列
%H·X=Y
%% 检测解调
% 均衡1(简单相位补偿)
HH=fft(h,M) ;
y6= fft(ys)/sqrt(M);
y_dect=y6.*conj(HH); %信道估计+均衡
y7=reshape(y_dect,[],1); %并串变换
yj=pskdemod(y7,4,pi/4); %qpsk解调
De_data1 = reshape(yj,[],1);
De_data2 = de2bi(De_data1,2);
w(:,jj)= reshape(De_data2',[],1); %转换同输入a形式,便于误码率计算
% 均衡2 Y=Hd*H*Hid*X+Hd*N
[sss,sssss]=size(H);
e=eig(H);
dftmtx(sss); %fft矩阵
dftmtx(sss)'; %因为fft矩阵为U阵,故ifft矩阵为其共轭转置
Hs=dftmtx(sss)*H*dftmtx(sss)' ; %均衡矩阵,对H做fft和ifft
y6s= fft(ys)/sqrt(M);
y_dects=pinv(Hs)*y6s; % 均衡*HS^-1
y7s=reshape(y_dects,[],1);
yjs=pskdemod(y7s,4,pi/4);
De_data1s = reshape(yjs,[],1);
De_data2s = de2bi(De_data1s,2);
ws(:,jj)= reshape(De_data2s',[],1);
end
q=reshape(w,1,2*M*N);
[number1,BER_S(ii)] = symerr(a,q); %计算错误比特数和误码率
qs=reshape(ws,1,2*M*N);
[number1,BER_Ss(ii)] = symerr(a,qs);%计算错误比特数和误码率
end
BER_S
BER_Ss
%% 绘制图形
figure;
semilogy(SNR,BER_S,'-r*');hold on;
axis([-1,20,10^-4,1]);
title('误码性能分析');
xlabel('信噪比SNR(dB)');ylabel('误码率BER');
figure
semilogy(SNR,BER_Ss,'-g*');hold on;
%text(10,0.01,'MMSE');
axis([-1,20,10^-4,1]);
title('误码性能分析');
xlabel('信噪比SNR(dB)');ylabel('误码率BER');
关于OFDM系统还有很多细节不理解,仍需学习,持续补充中!!!
相关博文
1.QPSK基础与多径信道Matlab仿真
2.QPSK/OFDM多径时变信道仿真