用简单仿真链路产生 WiFi CSI(不依赖专用工具箱,matlab实现)

此文章利用matlab实现简单仿真链路产生WiFi CSI的过程,不依赖专用工具箱,旨在让新手小白能更直观地清除WiFi CSI的产生机理,方便后续研究。此篇文章只做简单的仿真,更深入的请自己手动采数据或者移步别处。

目录

一、准备工作

二、基本参数设置

三、构造训练OFDM符

四、多径瑞利信道

五、逐天线时分发射并接收

六、CSI信道估计

七、幅值和相位可视化

八、模拟与真实对比


一、准备工作

首先,需要明确以下目标和参数:

1、定义OFDM与MIMO参数:例如 20 MHz、64点FFT、52个有效子载波、CP长度16、发射/接收天线数Nt​,Nr​。

2、构造训练符(LTF替身) :在实际802.11n/ac里用 HT-LTF/HE-LTF 获取CSI。为简洁,我们用"逐天线正交时分训练"(每次只开一个Tx,其他静默),这样在接收端就能直接做

3、信道建模 :给每个r,t 链路一个多径瑞利衰落脉冲响应(可选多普勒/CFO/采样偏差)。

4、通过信道发送 :对每个发射天线把OFDM训练块加CP后发送,经每个卷积并在各接收端相加,再叠加AWGN。

5、接收处理 :去CP、FFT→得到

6、估计CSI :对当前"激活"的发射天线 t,做 。顺次激活所有发射天线,拼成的CSI张量。

7、(可选)插值/平滑与LMMSE:多符号或导频内插;也可做子载波方向的Wiener平滑提升SNR。

二、基本参数设置

Matlab 复制代码
Nt = 2;                  % 发射天线数
Nr = 2;                  % 接收天线数
Nfft = 64;               % FFT点数(802.11a/n 20MHz)
Ng   = 16;               % 循环前缀长度
subc_idx = [-26:-1 1:26];% 52个有效子载波(跳过DC)
Nsc = numel(subc_idx);
Es  = 1;                 % 训练符平均功率
SNRdB = 25;              % 接收端SNR(可改)

三、构造训练OFDM符

用BPSK全已知子载波(实际LTF有特定序列,这里只需"已知且非零"即可)

Matlab 复制代码
Xfull = zeros(Nfft,1);
trainSymbols = (2*(randi([0 1],Nsc,1))-1); % BPSK +/-1
trainSymbols = sqrt(Es)*trainSymbols;      % 调整功率
Xfull(subc_idx + (subc_idx<0)*Nfft + 1) = trainSymbols;  % 映射到FFT bins
x_time = ifft(ifftshift(Xfull), Nfft);     % IFFT(使用ifftshift对齐DC)
tx_ofdm = [x_time(end-Ng+1:end); x_time];  % 加CP
Ns = length(tx_ofdm);

四、多径瑞利信道

瑞利衰落信道(Rayleigh fading channel)是一种无线电信号传播环境的统计模型。这种模型假设信号通过无线信道之后,其信号幅度是随机的,即"衰落",并且其包络服从瑞利分布。这一信道模型能够描述由电离层和对流层反射的短波信道,以及建筑物密集的城市环境。

Matlab 复制代码
% 设定一个离散PDP
tapDelays = [0 1 3 5 7];          % 以采样点为单位的延迟
tapPowers_dB = [0 -3 -6 -9 -12];  % 功率谱
tapPowers = 10.^(tapPowers_dB/10);
L = tapDelays(end)+1;

% 为每个链路生成独立脉冲响应
h = cell(Nr,Nt);
for r = 1:Nr
    for t = 1:Nt
        h_rt = zeros(L,1);
        for l = 1:numel(tapDelays)
            amp = sqrt(tapPowers(l)/2)*(randn+1j*randn);
            h_rt(tapDelays(l)+1) = amp;
        end
        h{r,t} = h_rt;
    end
end

五、逐天线时分发射并接收

Matlab 复制代码
Y = zeros(Nr,Nt,Nfft);  % 保存每次接收的频域符
noiseVarLin = Es/Nsc * 10^(-SNRdB/10);

for t = 1:Nt
    % 当前仅开启第t根发射天线,其它静默
    txSig_t = tx_ofdm;
    % 通过信道到各接收天线并叠加噪声
    for r = 1:Nr
        yr = conv(txSig_t, h{r,t});
        yr = yr(1:Ns); % 对齐长度(忽略尾符泄露,训练符足够长可避免IS I)
        % 加噪
        yr = yr + sqrt(noiseVarLin/2)*(randn(size(yr))+1j*randn(size(yr)));
        % 去CP、FFT
        y_noCP = yr(Ng+1:Ng+Nfft);
        Yfreq = fftshift(fft(y_noCP, Nfft));
        Y(r,t,:) = Yfreq; % 保存
    end
end

六、CSI信道估计

Matlab 复制代码
Hhat = zeros(Nr,Nt,Nsc); % 只保留有效子载波
Xused = Xfull(subc_idx + (subc_idx<0)*Nfft + 1); % 已知训练符频域值

for t = 1:Nt
    for r = 1:Nr
        Yrt = squeeze(Y(r,t,:));              % Nfft x 1
        Yused = Yrt(subc_idx + (subc_idx<0)*Nfft + 1);
        Hhat(r,t,:) = Yused ./ Xused;         % LS估计
    end
end

七、幅值和相位可视化

使用abs函数获取幅值,使用angle函数获取相位。

Matlab 复制代码
k = 1:Nsc;
H11 = squeeze(Hhat(1,1,:));
figure; plot(k, 20*log10(abs(H11))); grid on; xlabel('子载波索引'); ylabel('幅度(dB)');
title('估计CSI幅度(r=1,t=1)');
figure; plot(k, angle(H11)); grid on; xlabel('子载波索引'); ylabel('相位(rad)');
title('估计CSI相位(r=1,t=1)');

八、模拟与真实对比

模拟产生的CSI幅值:

真实产生的CSI幅值:

模拟产生的CSI相位

真实产生的CSI相位:

博主的每篇博文都是用心去写的,喜欢的可以多多支持和收藏,创作不易,未经作者允许,请勿转载或者抄袭。看WiFi指纹定位,我只认准全村第二帅和数产小黑娃,如外站有抄袭,记得点点举报!

关于WiFi 指纹定位迷茫的童鞋可以参考博主以前文章:WiFi指纹定位发论文求生指南------浅论WiFi指纹定位的前世今生与毕业困境-CSDN博客

相关推荐
卡尔曼的BD SLAMer15 小时前
计算机视觉与深度学习 | 基于深度学习的图像特征提取与匹配算法综述及MATLAB实现
人工智能·深度学习·算法·计算机视觉·matlab
yuan199971 天前
MATLAB中的蛙跳算法实现
算法·matlab
GoodG_study1 天前
Matlab函数转C语言供Keil使用
stm32·matlab·c
神里流~霜灭1 天前
Fourier 级数展开(案例:级数展开 AND 求和)
c语言·c++·算法·matlab·fourier 级数展开·级数展开求和·fourier算法
封奚泽优2 天前
数学七夕花礼(MATLAB版)
开发语言·数学·matlab·七夕·鲜花
yongui478344 天前
基于MATLAB/Simulink的单机带负荷仿真系统搭建
网络·matlab
ぁず4 天前
MATLAB中函数的详细使用
matlab
桃源学社(接毕设)4 天前
基于MATLAB的运动模糊图像修复方法研究(LW+源码+讲解+部署)
图像处理·深度学习·计算机视觉·matlab·毕业设计·图像滤波去噪
Evand J5 天前
【MATLAB例程】水下机器人长基线(LBL)定位,用于三维轨迹,使用EKF滤波,融合LBL和IMU,4个锚点(长基线基站数=4),附下载链接
开发语言·matlab·机器人