基于MATLAB的短时傅里叶变换及其逆变换的实现

简介: 基于MATLAB的短时傅里叶变换(STFT)及其逆变换(ISTFT)的实现

基于MATLAB的短时傅里叶变换(STFT)及其逆变换(ISTFT)的实现


一、核心代码实现

%% 清空环境
clear; clc; close all;

%% 参数设置
fs = 1000;          % 采样频率
t = 0:1/fs:2;       % 时间向量(2秒)
f1 = 50; f2 = 200;  % 信号频率成分
x = sin(2*pi*f1*t) + 0.5*sin(2*pi*f2*t);  % 原始信号

%% STFT参数
win_len = 256;      % 窗长(影响频率分辨率)
overlap = 128;      % 重叠长度(影响时间分辨率)
nfft = 512;         % FFT点数
window = hamming(win_len);  % 窗函数选择

%% 执行STFT
[S, f, t_stft] = stft_custom(x, fs, window, overlap, nfft);

%% 可视化STFT结果
figure;
imagesc(t_stft, f, 20*log10(abs(S)+eps));
axis xy; shading interp;
xlabel('时间 (s)'); ylabel('频率 (Hz)');
title('STFT时频谱图 (Hamming窗)');
colorbar;

%% 逆变换重建信号
x_recon = istft_custom(S, window, overlap, nfft, fs);

%% 重建效果验证
figure;
subplot(2,1,1);
plot(t, x); hold on;
plot(t, x_recon, '--r');
title('原始信号与重建信号对比');
xlabel('时间 (s)'); ylabel('幅值');
legend('原始信号', '重建信号');

subplot(2,1,2);
plot(t, x - x_recon);
title('重建误差');
xlabel('时间 (s)'); ylabel('误差幅值');

%% 自定义STFT函数
function [S, f, t] = stft_custom(x, fs, window, overlap, nfft)
    % 输入参数:
    % x: 输入信号
    % fs: 采样频率
    % window: 窗函数
    % overlap: 重叠长度
    % nfft: FFT点数

    [win_len, ~] = size(window);
    hop = win_len - overlap;  % 步长

    % 分帧处理
    num_frames = 1 + floor((length(x) - win_len)/hop);
    frames = zeros(num_frames, win_len);

    for i = 1:num_frames
        start_idx = (i-1)*hop + 1;
        frames(i,:) = x(start_idx:start_idx+win_len-1) .* window';
    end

    % 计算STFT
    S = fft(frames, nfft, 2);
    S = S(:,1:win_len/2+1);  % 单边频谱

    % 频率轴
    f = (0:win_len/2) * fs / win_len;
    % 时间轴
    t = (0:num_frames-1) * hop / fs;
end

%% 自定义ISTFT函数(最小二乘优化)
function x_recon = istft_custom(S, window, overlap, nfft, fs)
    % 输入参数:
    % S: STFT频谱
    % window: 窗函数
    % overlap: 重叠长度
    % nfft: FFT点数
    % fs: 采样频率

    [n_freq, n_frames] = size(S);
    win_len = length(window);
    hop = win_len - overlap;

    % 初始化重建信号
    x_recon = zeros((n_frames-1)*hop + win_len, 1);

    % 重叠相加法
    for i = 1:n_frames
        % 逆FFT
        frame = ifft(S(:,i) .* conj(S(:,i)), nfft);
        frame = real(frame(1:win_len));

        % 重叠相加
        start_idx = (i-1)*hop + 1;
        x_recon(start_idx:start_idx+win_len-1) = ...
            x_recon(start_idx:start_idx+win_len-1) + frame;
    end

    % 窗函数能量归一化
    x_recon = x_recon ./ sum(window.^2);
end

二、关键参数说明

参数 作用范围 推荐值 影响效果
win_len 窗函数长度 256-4096 窗越长频率分辨率越高
overlap 帧间重叠量 50%-75% 重叠越多时间分辨率越高
nfft FFT点数 ≥窗长 影响频率采样密度
window 窗函数类型 Hamming/Hann 不同窗影响频谱泄漏特性

三、应用场景示例

1. 语音信号分析

% 加载语音信号
[语音, fs] = audioread('speech.wav');
语音 =语音(:,1); % 单声道

% STFT参数设置
win_len = 512; overlap = 256;

% 计算并绘制语谱图
[S,f,t] = stft_custom(语音, fs, hamming(win_len), overlap, 1024);
imagesc(t, f, 20*log10(abs(S)+eps));
title('语音信号语谱图');

2. 机械故障检测

% 加载振动信号
[vibration, fs] = load_vibration_data();

% STFT分析
[S,f,t] = stft_custom(vibration, fs, hanning(1024), 512, 2048);

% 特征提取(频域能量)
energy = sum(abs(S), 1);
plot(t, energy);
title('振动信号频域能量分布');

四、注意事项

  1. 窗函数选择 短时分析需满足常数重叠相加(COLA)条件,推荐使用Hann/Hamming窗 窗长与信号频率成分匹配:高频信号用短窗,低频信号用长窗

  2. 频谱泄漏抑制

    • 增加窗长可减少频谱泄漏

    • 使用加窗函数后需进行能量归一化:

      S = S .* sum(window.^2);
      
  3. 实时性处理 对实时信号需设置固定帧长和重叠 使用overlap-add方法保证时域连续性

参考代码 短时傅立叶变换及其逆变换源程序 www.youwenfan.com/contentale/78965.html

该方法通过合理选择窗函数和参数设置,实现了高精度的时频分析。

相关文章
|
监控 网络协议 Unix
Linux命令-nc(端口监控、文件传输、反弹shell等)
Linux命令-nc(端口监控、文件传输、反弹shell等)
969 0
|
6月前
|
数据采集 算法
matlab实现合成孔径成像的三种算法
matlab实现合成孔径成像的三种算法
|
1月前
|
人工智能 IDE 编译器
如何用给各种IDE配置R语言环境
R语言虽无Python式虚拟环境,但通过Conda管理或多项目隔离方案(如自定义.libPaths或使用renv工具),可实现包依赖独立、版本锁定与环境复现,支持跨平台迁移与协作,真正做到“一次配置,永久可用”。推荐renv+RStudio组合,高效管理项目环境。
|
Java Maven
IDEA 2018 2020 2021 2022 各版本对Maven版本兼容问题汇总
Maven3.6.3版本兼容问题 错误信息如下: 测试范围如下图: 注意:针对一些老项目 还是尽量采用 3.6.3版本,针对idea各个版本的兼容性就很兼容 0.IDEA 2022 兼容maven 3.8.1及之前的所用版本 1.IDEA 2021 兼容maven 3.8.1及之前的所用版本 2.IDEA 2020 兼容Maven 3.6.3及之前所有版本 3.IDEA 2018 兼容Maven3.6.1及之前所有版本
5097 0
IDEA 2018 2020 2021 2022 各版本对Maven版本兼容问题汇总
|
缓存 监控 负载均衡
SpringCloud极简入门-Eureka集群&Eureka调优
当微服务数量达到上百之数,一个EurekaServer所需要承担的压力会比较大,加上单节点故障问题可能会导致整个微服务不可被访问,由于EurekaServer在微服务中举足轻重,我们需要考虑对EurekaServer做高可用集群。
573 0
|
27天前
|
自然语言处理 算法 API
AiPy:AI+Python=安上手脚的Agent
AiPy融合LLM与Python生态,首创“代码即代理”模式,实现需求解析、代码生成、自动执行到动态调优的全流程闭环。支持全本地化部署,保障数据安全,深度集成Python工具链,适配多模型与跨平台环境,赋能企业零代码自动化。(238字)
|
10月前
|
Ubuntu Linux 测试技术
Python 虚拟环境配置
本文总结了 Python 开发中的环境配置、常用操作和常见错误处理。重点介绍了如何使用 `virtualenv` 搭建虚拟环境,解决依赖冲突问题,并保持系统环境的干净。同时,详细说明了依赖库的安装与管理方法,包括使用 `pip install` 安装依赖、生成和使用 `requirements.txt` 文件,以及查看 Python 文档和修改环境变量等实用技巧。
752 60
|
机器学习/深度学习
一文看懂卷积运算(convolution)与互相关运算(cross-correlation)的区别
一文看懂卷积运算(convolution)与互相关运算(cross-correlation)的区别
|
Ubuntu Shell
ubuntu卸载conda
ubuntu卸载conda
1397 1
|
JavaScript 开发工具 git
使用webstorm来创建并且运行vue项目详细教程
使用webstorm来创建并且运行vue项目详细教程
1592 0