OFDM技术原理及系统MATLAB仿真
Posted 一只学习的猫
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了OFDM技术原理及系统MATLAB仿真相关的知识,希望对你有一定的参考价值。
1 前言
最近除了在看信道相关的内容,还学习了一些OFDM相关的技术原理,并进行了简单的仿真。继续记录~~~
欢迎感兴趣的朋友一起交流分享。
2 OFDM技术原理
首先给出一个OFDM系统的系统框图,然后再对其中的关键点进行介绍。
2.1 子载波之间的正交性
我们知道OFDM作为一种多载波并行传输技术,一个很大的优点就是频带利用率高,因为他的子载波具有正交性。
我们最开始接触正交性,其实是一个数学概念:两个信号的乘积在一个周期内的积分为0,我们则认为这两个信号是正交的。也正是利用这一点,接收端可以通过对每一路乘以不同的因子,然后积分运算解调出对应路的信息,而不受其它路信号的干扰。需要注意的是,时延可能会影响子载波之间的正交性,从而导致解调错误,因此会在OFDM符号周期的前面添加循环前缀以消除这种影响,这在后面会讲到。
对于OFDM系统来说,从时域上来看是这样子的:
但是从频域上来看正交性如何提高了频带利用率可能更直观一些,我们进行一个简单的matlab仿真,假设有四个正交子载波承载信息,把他们的频谱画在一起,是这个样子的:
可以看到相比一般的FDM系统,子载波频谱发生了交叠,频带利用率更高。
还可以参考博客:
(https://blog.csdn.net/madongchunqiu/article/details/18614233/?utm_medium=distribute.pc_relevant.none-task-blog-baidujs_title-1&spm=1001.2101.3001.4242)
我觉得讲解的非常形象,想了解的更多更详细的朋友可以看看。
补充:给出一个有频偏的情况下,OFDM系统的解调性能。
clear all;
close all;
N=8; % 子载波数
f=1:N; % 各个子载波频率
x=randi([0 3],1,N); % 子载波上的数据
x1=qammod(x,4); % 4-QAM调制
t=0:0.001:1-0.001; % 符号持续时间
w=2*pi*f.'*t;
w1=2*pi*(f+0.2).'*t; % 频偏为0.2Hz时的子载波频率
y=x1*exp(j*w); % 子载波调制
figure(1)
plot(t,abs(y)) % 画出调制后的波形包络
for ii=1:N
y1(ii)=sum(y.*exp(-j*w(ii,:)))/length(t); %无频偏解调第ii个子载波上的数据
end
figure(2)
stem(abs(x1)) % 显示无频偏时子载波解调后的结果
hold on
stem(abs(y1),'r<')
title('频偏为0时的子载波解调结果')
axis([0 9 0 3])
legend('原始数据','子载波解调后的数据')
% 存在频率偏差时的子载波解调结果
for ii=1:N
y3(ii)=sum(y.*exp(-j*(w1(ii,:))))/length(t);
end
figure(3)
stem(abs(x1))
hold on
stem(abs(y3),'r<')
axis([0 9 0 3])
title('频偏为0.2Hz时的子载波解调结果')
legend('原始数据','子载波解调后的数据')
仿真结果如下:
可以发现当有频偏时,OFDM系统解调的性能会变差。
2.2 IFFT和FFT
首先我们给出离散傅里叶变换和离散傅里叶逆变换的公式:
接下来我们推导为什么OFDM调制等价于一个离散傅里叶逆变换。一个OFDM调制的过程:OFDM发射机将信息比特流映射成一个PSK或QAM符号序列 ,之后将符号序列转换为 个并行符号流。每 个经过串/并转换的符号被不同的子载波调制,生成1个OFDM符号。
2.3 循环前缀的作用
加入保护间隔的作用主要是两个,其一是抑制符号间串扰(ISI),一个是抑制子载波间干扰(ICI)。
为了抑制符号间干扰,可以在两个OFDM符号之间插入保护间隔。插入保护间隔的方式有两种,一种是直接插入空白(插入0),只要插入的保护间隔长度大于信道的最大传播时延,就可以完全消除ISI,然而这样并不能解决多径带来的子载波间干扰问题(假设第2个子载波存在时延,那么将导致在一个OFDM符号周期内,第2子载波不包括整数个周期波形,在解调时会对第一个子载波造成干扰)。为了消除由于多径导致的ICI,引入了第二种插入保护间隔的方法:插入循环前缀,将OFDM符号周期内的最后若干个点搬移导OFDM符号的前面。
下面给出一个OFDM系统加入空白前缀和循环前缀的系统性能对比仿真:
clear all;
close all;
N=64; % 系统子载波数
x=randi([0 15],N,2); % 2个符号周期的数据
x1=qammod(x,16); % 16-QAM调制
x2=ifft(x1); % IFFT
x3=[zeros(16,2); x2]; % 空白前缀
x4=[x2(49:end,:); x2]; % 循环前缀
x3=reshape(x3,1,160); % 并串变换
x4=reshape(x4,1,160);
h=sqrt(1/3)*(randn(1,3)); % 3径信道
y1=x3*h(1)+[zeros(1,8) x3(1:end-8)*h(2)]; %只考虑前2径
y2=x4*h(1)+[zeros(1,8) x4(1:end-8)*h(2)];
y3=reshape(y1,80,2); % 串并变换
y4=reshape(y2,80,2);
y3=y3(17:end,2); % 考虑第2个符号的影响
y4=y4(17:end,2);
y3=fft(y3); % FFT
y4=fft(y4);
h1=[h(1) zeros(1,7) h(2)]; % 信道FFT变换
H=fft(h1,N).';
y3=y3./H; % 信道均衡
y4=y4./H;
stem(abs(x1(:,2)),'fill');hold on;stem(abs(y3),'r<');stem(abs(y4),'-gs')
legend('原始信号','空白前缀','循环前缀')
axis([0 70 0 max(abs(y3))+2])
title('2径信道结果')
y1=y1+[zeros(1,20) x3(1:end-20)*h(3)]; % 3径信道结果
y2=y2+[zeros(1,20) x4(1:end-20)*h(3)];
y3=reshape(y1,80,2); % 串并变换
y4=reshape(y2,80,2);
y3=y3(17:end,2); % 考虑第2个符号的影响
y4=y4(17:end,2);
y3=fft(y3); % FFT
y4=fft(y4);
h1=[h1 zeros(1,11) h(3)]; % 信道FFT变换
H=fft(h1,N).';
y3=y3./H; % 信道均衡
y4=y4./H;
figure
stem(abs(x1(:,2)),'fill');hold on;stem(abs(y3),'r<');stem(abs(y4),'-gs')
legend('原始信号','空白前缀','循环前缀')
axis([0 70 0 max(max(abs(y3),abs(y4)))+2])
title('3径信道结果')
仿真结果如下:
从上图中可以看出,在2径信道的情况下,经过信道均衡后,添加了循环前缀的第2个OFDM符号没有受到第一个OFDM符号和子载波间的干扰,而添加空白前缀的符号受到子载波间干扰的影响,因此解调结果与原始数据不一致。
在多径时延大于循环前缀的长度时,无法消除码间串扰,第2个OFDM符号受到第一个OFDM符号的干扰。
3 OFDM系统仿真
在对OFDM系统的一些比较重要的知识点进行介绍之后,下面给出一个OFDM系统的仿真主程序:
clear all;
close all;
clc;
Nsymbol = 100; % OFDM符号个数
Ncarrier = 256; % 子载波个数
space_pilot_carrier = 5; % 子载波间隔
space_pilot_time = 10; % 时域导频间隔
N_pilot_time = Nsymbol/space_pilot_time; % 时域导频个数
N_pilot_carrier = (Ncarrier-1)/space_pilot_carrier+1; % 频域导频个数
N_sym_pilot = N_pilot_carrier*N_pilot_time; % 导频符号数
N_valid_sym = Nsymbol*Ncarrier-N_sym_pilot; % 有效符号数
Nvalid_data = N_valid_sym; % 有效的输入二进制比特数
len_cp = 64; % 循环前缀长度
origdata = randi([0,3],1,N_valid_sym); %% 有效的符号
modulation_type = 'QPSK'; % 子载波调制类型 1: QPSK,2:16QAM,3:64QAM
fs = 4e6; % 采样率
Ts = 1/fs; % 采样周期 单位s
sym_constell = pskmod(origdata,4); % 映射后的有效符号
value = 1; % 插入导频值为1
% 生成数据矩阵
data_matrix = zeros(Ncarrier,Nsymbol);
count = 1;
for nn=1:Nsymbol
for mm = 1:Ncarrier
if ((mod(mm,space_pilot_carrier)==1)&&(mod(nn,space_pilot_time)==1))
data_matrix(mm,nn) = value;
else
data_matrix(mm,nn) = sym_constell(count);
count = count+1;
end
end
end
% IFFT
Tx_data = ifft(data_matrix,Ncarrier);
% 加CP
Tx_data_add_cp = [Tx_data(Ncarrier-len_cp+1:Ncarrier,:);Tx_data];
% 并串转换
len_row = len_cp+Ncarrier; % 行数
len_column = Nsymbol; % 列数
len_tx = len_row*len_column; % 总符号数
Tx_data_stream = zeros(1,len_tx);
count_tx = 1;
for ss = 1:len_column
for kk = 1:len_row
Tx_data_stream(count_tx) = Tx_data_add_cp(kk,ss);
count_tx =count_tx+1;
end
end
Terrain_Index = 'RA';
Doppler=120;% 最大多普勒频移,决定了信道的时变快慢,当v=60km/h,fc = 2.4G时,fdmax = 133Hz
SNR = -10:1:30;
for ii = 1:length(SNR)
snr = SNR(ii);
% 通过COST207信道
[data_receive,tap_coff,sigma2_w]=Channel_pass_COST207(Tx_data_stream, Terrain_Index, Nsymbol,Ts, snr, Doppler);
% 串并转换
data_r = reshape(data_receive,len_row,[]);
% 去除循环前缀
data_r_no_cp = data_r(len_cp+1:end,:);
% FFT
data_r_fft = fft(data_r_no_cp,Ncarrier);
% 二维线性插值信道估计及均衡
[equa_2D_linear_data,MSE_linear_interp_2D] = linear_interp_2D_chann_estimation(data_r_fft,Nsymbol,Ncarrier,N_pilot_carrier,N_pilot_time,space_pilot_carrier,space_pilot_time,tap_coff);
% 去导频
throwpilot_data = remove_pilot(equa_2D_linear_data,Nsymbol,modulation_type,N_pilot_carrier,N_pilot_time,space_pilot_carrier,space_pilot_time);
% 逆映射
demod_data=pskdemod(throwpilot_data,4);
% 误码率性能
[err_num_sym(ii),err_rate_sym(ii)]=symerr(origdata,demod_data);
disp('err_num_sym:');
disp(err_num_sym(ii));
disp('err_rate_sym:');
disp(err_rate_sym(ii));
end
figure(1)
plot(SNR,err_rate_sym*100,'linewidth',1);
xlabel('SNR/dB');
ylabel('误码率/%');
仿真的结果:
4 总结
以上主要是介绍了OFDM技术的一些基础知识,对于OFDM系统中的关键模块都有相关的算法研究,比如同步、信道估计、符号检测等等,希望后面能有更深入的了解。
参考书籍:
《详解MATLAB/Simulink通信系统建模与仿真》
以上是关于OFDM技术原理及系统MATLAB仿真的主要内容,如果未能解决你的问题,请参考以下文章
现代通信基于matlab OFDM通信系统仿真含Matlab源码 1005期