1. 序言

2. 功率谱密度理论基础简述

3. Matlab 中 PSD 函数的使用

3.1 传统非参数方法估计 PSD

3.2 参数方法估计 PSD

4. 实验示例

4.1 实验数据

%% 导入数据
% 1000 Hz 记录了 500 ms
% 采样率 1000 Hz
srate = 1000;
[frames, channels, epochs] = size(x_train);

rightwards = sum(y_train);
leftwards = length(y_train) - rightwards;
fprintf('一共有 %d 个训练样本，其中往左运动有 %d 个，往右运动有 %d 个\n',...
length(y_train), leftwards, rightwards);

一共有 316 个训练样本，其中往左运动有 159 个，往右运动有 157 个


## 4.2 提取特征

%% 提取 PSD 特征
function [power_features] = ExtractPowerSpectralFeature(eeg_data, srate)
% 从 EEG 信号中提取功率谱特征
%   Parameters:
%       eeg_data:   [channels, frames] 的 EEG 信号数据
%       srate:      int, 采样率
%   Returns:
%       eeg_segments:   [1, n_features] vector

%% 计算各个节律频带的信号功率
[pxx, f] = pwelch(eeg_data, [], [], [], srate);
power_delta = bandpower(pxx, f, [0.5, 4], 'psd');
power_theta = bandpower(pxx, f, [4, 8], 'psd');
power_alpha = bandpower(pxx, f, [8, 14], 'psd');
power_beta = bandpower(pxx, f, [14, 30], 'psd');

% 求 pxx 在通道维度上的平均值
mean_pxx = mean(pxx, 2);
% 简单地堆叠起来构成特征（可以用更高级地方法，比如考虑通道之间的相关性的方法构成特征向量）
power_features = [
power_delta, power_theta, ...
power_alpha, power_beta, ...
mean_pxx(1:12)';
];

end


X_train_features = [];
for i = 1:epochs
% 取出数据
eeg_data = squeeze(x_train(:, :, i));
feature = ExtractPowerSpectralFeature(eeg_data, srate);
X_train_features = [X_train_features; feature];
end
% 原始的 y_train 是行向量，展开成列向量
y_train = y_train(:);


## 4.3 分类

% 由于只是简单演示，所以不划分训练集、交叉验证集
model = fitcsvm(X_train_features, y_train,...
'Standardize', true, 'KernelFunction', 'RBF', 'KernelScale', 'auto', 'verbose', 1);

y_pred = model.predict(X_train_features);
acc = sum(y_pred == y_train) / length(y_pred);
fprintf('Train Accuracy: %.2f%%\n', acc * 100);


|===================================================================================================================================|
|   Iteration  | Set  |   Set Size   |  Feasibility  |     Delta     |      KKT      |  Number of   |   Objective   |   Constraint  |
|              |      |              |      Gap      |    Gradient   |   Violation   |  Supp. Vec.  |               |   Violation   |
|===================================================================================================================================|
|            0 |active|          316 |  9.968454e-01 |  2.000000e+00 |  1.000000e+00 |            0 |  0.000000e+00 |  0.000000e+00 |
|          350 |active|          316 |  5.175246e-05 |  9.741516e-04 |  5.129944e-04 |          312 | -1.850933e+02 |  5.967449e-16 |

Train Accuracy: 94.62%