LSTM分类详细介绍

源码

什么是LSTM分类?

LSTM分类(Long Short-Term Memory Classification)是一种基于**长短期记忆网络(Long Short-Term Memory, LSTM)**的分类方法。LSTM是一种特殊的递归神经网络(Recurrent Neural Network, RNN),设计用于处理和预测序列数据中的长期依赖关系。与传统的RNN相比,LSTM通过其独特的门控机制(输入门、遗忘门和输出门)有效地缓解了梯度消失和爆炸问题,能够记忆和遗忘信息,从而在处理长序列数据时表现出色。

LSTM分类的组成部分
  1. 数据预处理

    • 数据导入与整理:读取分类任务所需的序列数据,处理缺失值和异常值,确保数据质量。
    • 数据构造:将序列数据转换为适合LSTM网络输入的格式,通常包括时间步长的设置和输入输出对的构建。
    • 数据归一化:对输入数据进行归一化或标准化处理,以加快训练速度和提高模型稳定性。
  2. LSTM模型构建

    • 定义网络结构:设定LSTM网络的层数、每层的神经元数量以及其他网络参数。
    • 添加激活层和全连接层:在LSTM层后添加激活函数(如ReLU)和全连接层,以实现分类任务。
  3. 模型训练与预测

    • 设置训练参数:定义优化算法、学习率、批量大小、迭代次数等训练参数。
    • 模型训练:使用训练集数据训练LSTM模型,优化网络权重。
    • 模型预测:使用训练好的LSTM模型对训练集和测试集数据进行预测,得到分类结果。
  4. 结果分析与可视化

    • 性能指标计算:计算分类准确率、混淆矩阵等指标,评估模型的分类性能。
    • 绘制对比图:绘制训练集和测试集的真实类别与预测类别对比图,直观展示模型的分类效果。
    • 混淆矩阵:绘制混淆矩阵,分析分类错误的具体情况。
LSTM分类的优势
  1. 捕捉长期依赖关系

    • LSTM通过其门控机制能够记忆和利用序列中的长期依赖信息,适用于处理具有时间依赖性的序列数据。
  2. 抗梯度消失和爆炸

    • 与传统RNN相比,LSTM有效缓解了梯度消失和爆炸问题,使得网络能够更好地训练深层结构。
  3. 灵活的网络结构

    • LSTM网络结构灵活,可以根据任务需求调整层数和每层的神经元数量,适应不同复杂度的分类任务。
  4. 广泛的应用领域

    • LSTM在自然语言处理、时间序列分析、语音识别等多个领域表现出色,具有广泛的应用前景。
LSTM分类的应用

LSTM分类广泛应用于需要处理序列数据的各种分类任务,包括但不限于:

  1. 自然语言处理

    • 文本分类:将文本数据分类为不同的类别,如情感分析、垃圾邮件检测等。
    • 语言识别:识别文本的语言类型。
  2. 时间序列分析

    • 故障检测:根据设备的时间序列数据检测潜在的故障类别。
    • 行为识别:识别用户的行为类别,如运动类型分类。
  3. 语音识别

    • 语音命令分类:将语音命令分类为不同的操作指令。
    • 说话人识别:根据语音特征识别说话人的身份类别。
  4. 金融预测

    • 信用评分:根据客户的历史金融数据预测信用评分类别。
    • 市场情绪分类:根据市场数据分类市场情绪状态。
  5. 医疗健康

    • 疾病分类:根据患者的医疗记录分类疾病类型。
    • 症状识别:根据症状数据分类健康状态。
如何使用LSTM分类

使用LSTM分类模型主要包括以下步骤:

  1. 准备数据集

    • 数据收集与整理:确保序列数据的完整性和准确性,处理缺失值和异常值。
    • 数据构造:将序列数据转换为适合LSTM网络输入的格式,包括时间步长的设置和输入输出对的构建。
    • 数据归一化:对输入数据进行归一化或标准化处理,以加快训练速度和提高模型稳定性。
  2. 构建LSTM模型

    • 定义网络结构:设定LSTM网络的层数、每层的神经元数量,以及添加必要的激活层和全连接层。
    • 设置训练参数:定义优化算法(如Adam)、学习率、批量大小、迭代次数等训练参数。
  3. 模型训练与预测

    • 模型训练:使用训练集数据训练LSTM模型,优化网络权重。
    • 模型预测:使用训练好的LSTM模型对训练集和测试集数据进行预测,得到分类结果。
  4. 模型评估与优化

    • 计算性能指标:计算分类准确率、混淆矩阵等指标,全面评估模型的分类性能。
    • 优化模型参数:根据性能指标调整LSTM模型的参数(如学习率、网络结构等),进一步优化模型性能。
  5. 结果分析与可视化

    • 预测结果对比图:绘制训练集和测试集的真实类别与预测类别对比图,直观展示模型的分类效果。
    • 混淆矩阵:绘制混淆矩阵,分析分类错误的具体情况。

MATLAB代码(添加详细中文注释)

以下是包含详细中文注释的LSTM分类MATLAB代码。

%% 初始化
clear              % 清除工作区中的所有变量,确保没有残留变量影响结果
close all          % 关闭所有打开的图形窗口,确保绘图环境的干净
clc                % 清空命令行窗口,提升可读性
warning off        % 关闭所有警告信息,避免运行过程中显示不必要的警告

%% 读取数据
res = xlsread('数据集.xlsx');  % 从Excel文件中读取数据,假设数据的最后一列为类别标签
% res变量存储了读取的数据,数据应按照时间顺序排列

%% 分析数据
num_class = length(unique(res(:, end)));  % 获取类别数,假设数据的最后一列是类别标签
num_dim = size(res, 2) - 1;               % 特征维度,即总列数减去类别列
num_res = size(res, 1);                   % 样本数,即数据的行数
num_size = 0.7;                           % 训练集占数据集的比例,这里设定为70%
res = res(randperm(num_res), :);          % 打乱数据集顺序(如果不需要打乱数据集,注释该行)
flag_conusion = 1;                        % 是否绘制混淆矩阵的标志(1为绘制,0为不绘制)

%% 设置变量存储数据
P_train = []; P_test = [];  % 输入数据:训练集和测试集
T_train = []; T_test = [];  % 输出数据:训练集和测试集

%% 划分数据集
for i = 1 : num_class
    mid_res = res((res(:, end) == i), :);           % 提取当前类别的数据
    mid_size = size(mid_res, 1);                    % 当前类别的样本个数
    mid_train_size = round(num_size * mid_size);    % 该类别的训练样本数
    
    % 划分训练集和测试集
    P_train = [P_train; mid_res(1: mid_train_size, 1: end - 1)];  % 训练集输入数据
    T_train = [T_train; mid_res(1: mid_train_size, end)];         % 训练集输出数据
    
    P_test  = [P_test; mid_res(mid_train_size + 1: end, 1: end - 1)];  % 测试集输入数据
    T_test  = [T_test; mid_res(mid_train_size + 1: end, end)];         % 测试集输出数据
end
% 通过逐类别划分,确保训练集和测试集在每个类别中都有代表性

%% 数据转置
P_train = P_train'; P_test = P_test';  % 转置输入数据,使每列为一个样本
T_train = T_train'; T_test = T_test';  % 转置输出数据,使每列为一个样本

%% 得到训练集和测试样本个数
M = size(P_train, 2);  % 训练集样本数
N = size(P_test , 2);  % 测试集样本数

%% 数据归一化
[P_train, ps_input] = mapminmax(P_train, 0, 1);  % 对训练集输入特征进行归一化,范围[0,1]
P_test  = mapminmax('apply', P_test, ps_input);  % 使用训练集的归一化参数对测试集输入特征进行归一化

t_train = categorical(T_train)';  % 将训练集输出数据转换为分类类型,并转置
t_test  = categorical(T_test )';  % 将测试集输出数据转换为分类类型,并转置

%% 数据平铺
% 将数据平铺为1维数据(可选择平铺为2维或3维数据,需调整模型结构)
P_train = double(reshape(P_train, num_dim, 1, 1, M));  % 训练集数据平铺为4维数组 (特征维度 × 1 × 1 × 样本数)
P_test  = double(reshape(P_test , num_dim, 1, 1, N));  % 测试集数据平铺为4维数组 (特征维度 × 1 × 1 × 样本数)

%% 数据格式转换
% 将数据按样本重新整理为单元格数组,适应trainNetwork函数的输入要求
for i = 1 : M
    p_train{i, 1} = P_train(:, :, 1, i);  % 训练集数据存储,每个单元格包含一个样本的特征向量
end

for i = 1 : N
    p_test{i, 1}  = P_test(:, :, 1, i);  % 测试集数据存储,每个单元格包含一个样本的特征向量
end

%% 建立 LSTM 网络模型
layers = [
    sequenceInputLayer(num_dim)  % 输入层,输入数据的维度是特征数
    
    lstmLayer(6, 'OutputMode', 'last')  % LSTM层,包含6个LSTM单元,输出最后一个时间步的结果
    reluLayer                         % ReLU激活层,增加网络的非线性
    
    fullyConnectedLayer(num_class)     % 全连接层,输出为类别数
    softmaxLayer                      % Softmax层,将输出转换为概率分布
    classificationLayer];              % 分类层,计算损失并进行分类

%% 参数设置
options = trainingOptions('adam', ...      % 选择Adam优化算法
    'MaxEpochs', 1000, ...                 % 最大训练迭代次数设为1000
    'InitialLearnRate', 0.01, ...          % 初始学习率设为0.01
    'LearnRateSchedule', 'piecewise', ...  % 学习率下降策略设为分段下降
    'LearnRateDropFactor', 0.1, ...        % 学习率下降因子设为0.1
    'LearnRateDropPeriod', 750, ...        % 每750次迭代后学习率下降
    'Shuffle', 'every-epoch', ...          % 每个epoch结束后打乱数据集
    'ValidationPatience', Inf, ...         % 关闭验证,即不进行验证
    'L2Regularization', 1e-4, ...          % L2正则化参数设为1e-4,防止过拟合
    'Plots', 'training-progress', ...      % 绘制训练过程的进度图
    'Verbose', false);                     % 关闭训练过程中的详细信息显示

%% 训练模型
net = trainNetwork(p_train, t_train, layers, options);  % 使用训练数据训练LSTM网络

%% 预测模型
t_sim1 = predict(net, p_train);  % 对训练集数据进行预测,得到训练集预测结果
t_sim2 = predict(net, p_test );  % 对测试集数据进行预测,得到测试集预测结果

%% 反归一化
T_sim1 = vec2ind(t_sim1');  % 将训练集预测结果的概率向量转换为类别索引
T_sim2 = vec2ind(t_sim2');  % 将测试集预测结果的概率向量转换为类别索引

%% 性能评价
error1 = sum((T_sim1 == T_train)) / M * 100;  % 计算训练集的分类准确率(百分比)
error2 = sum((T_sim2 == T_test )) / N * 100;  % 计算测试集的分类准确率(百分比)

%% 绘制网络分析图
analyzeNetwork(layers);  % 可视化和分析LSTM网络的结构

%% 绘图
% 绘制训练集和测试集预测结果对比图

% 绘制训练集预测结果对比图
figure
plot(1: M, T_train, 'r-*', 1: M, T_sim1, 'b-o', 'LineWidth', 1) % 绘制训练集真实类别与预测类别的对比曲线,红色星形标记为真实值,蓝色圆形标记为预测值
legend('真实值', '预测值')                                        % 添加图例,区分真实值和预测值
xlabel('预测样本')                                                % 设置X轴标签为“预测样本”
ylabel('预测结果')                                                % 设置Y轴标签为“预测结果”
string = {'训练集预测结果对比'; ['准确率=' num2str(error1) '%']};  % 创建标题字符串,包括准确率
title(string)                                                    % 添加图形标题
grid                                                             % 显示网格,提升图形的可读性

% 绘制测试集预测结果对比图
figure
plot(1: N, T_test, 'r-*', 1: N, T_sim2, 'b-o', 'LineWidth', 1)   % 绘制测试集真实类别与预测类别的对比曲线,红色星形标记为真实值,蓝色圆形标记为预测值
legend('真实值', '预测值')                                        % 添加图例,区分真实值和预测值
xlabel('预测样本')                                                % 设置X轴标签为“预测样本”
ylabel('预测结果')                                                % 设置Y轴标签为“预测结果”
string = {'测试集预测结果对比'; ['准确率=' num2str(error2) '%']};   % 创建标题字符串,包括准确率
title(string)                                                    % 添加图形标题
grid                                                             % 显示网格,提升图形的可读性

%% 混淆矩阵
if flag_conusion == 1
    % 绘制训练集的混淆矩阵
    figure
    cm = confusionchart(T_train, T_sim1);                % 创建训练集的混淆矩阵
    cm.Title = '训练集混淆矩阵';                             % 设置混淆矩阵标题
    cm.ColumnSummary = 'column-normalized';               % 设置列摘要为列归一化
    cm.RowSummary = 'row-normalized';                     % 设置行摘要为行归一化
    
    % 绘制测试集的混淆矩阵
    figure
    cm = confusionchart(T_test, T_sim2);                 % 创建测试集的混淆矩阵
    cm.Title = '测试集混淆矩阵';                             % 设置混淆矩阵标题
    cm.ColumnSummary = 'column-normalized';               % 设置列摘要为列归一化
    cm.RowSummary = 'row-normalized';                     % 设置行摘要为行归一化
end

代码说明

1. 初始化
clear              % 清除工作区中的所有变量,确保没有残留变量影响结果
close all          % 关闭所有打开的图形窗口,确保绘图环境的干净
clc                % 清空命令行窗口,提升可读性
warning off        % 关闭所有警告信息,避免运行过程中显示不必要的警告
  • clear:清除MATLAB工作区中的所有变量,确保代码运行环境的干净。
  • close all:关闭所有打开的图形窗口,避免之前的图形干扰当前的绘图。
  • clc:清空命令行窗口,提升可读性。
  • warning off:关闭MATLAB中的所有警告信息,避免在代码运行过程中显示不必要的警告。
2. 读取数据
res = xlsread('数据集.xlsx');  % 从Excel文件中读取数据,假设数据的最后一列为类别标签
% res变量存储了读取的数据,数据应按照时间顺序排列
  • xlsread:从指定的Excel文件数据集.xlsx中读取数据。
  • res:存储读取的数据,假设数据的最后一列为类别标签,其他列为特征。
3. 分析数据
num_class = length(unique(res(:, end)));  % 获取类别数,假设数据的最后一列是类别标签
num_dim = size(res, 2) - 1;               % 特征维度,即总列数减去类别列
num_res = size(res, 1);                   % 样本数,即数据的行数
num_size = 0.7;                           % 训练集占数据集的比例,这里设定为70%
res = res(randperm(num_res), :);          % 打乱数据集顺序(如果不需要打乱数据集,注释该行)
flag_conusion = 1;                        % 是否绘制混淆矩阵的标志(1为绘制,0为不绘制)
  • num_class:计算数据中的类别数量,通过对最后一列(类别标签)进行唯一值计数。
  • num_dim:计算特征的维度,即数据的总列数减去类别列。
  • num_res:计算数据的样本数量,即数据的行数。
  • num_size:设定训练集占整个数据集的比例,这里设定为70%。
  • randperm(num_res):生成一个1到num_res的随机排列,用于打乱数据集顺序,确保训练集和测试集的分布均匀。如果不需要打乱数据集,可以注释该行。
  • flag_conusion:设置是否绘制混淆矩阵的标志,1表示绘制,0表示不绘制。
4. 设置变量存储数据
P_train = []; P_test = [];  % 输入数据:训练集和测试集
T_train = []; T_test = [];  % 输出数据:训练集和测试集
  • P_trainP_test:初始化训练集和测试集的输入数据存储变量。
  • T_trainT_test:初始化训练集和测试集的输出数据存储变量。
5. 划分数据集
for i = 1 : num_class
    mid_res = res((res(:, end) == i), :);           % 提取当前类别的数据
    mid_size = size(mid_res, 1);                    % 当前类别的样本个数
    mid_train_size = round(num_size * mid_size);    % 该类别的训练样本数
    
    % 划分训练集和测试集
    P_train = [P_train; mid_res(1: mid_train_size, 1: end - 1)];  % 训练集输入数据
    T_train = [T_train; mid_res(1: mid_train_size, end)];         % 训练集输出数据
    
    P_test  = [P_test; mid_res(mid_train_size + 1: end, 1: end - 1)];  % 测试集输入数据
    T_test  = [T_test; mid_res(mid_train_size + 1: end, end)];         % 测试集输出数据
end
  • for i = 1 : num_class:遍历每个类别。
  • mid_res = res((res(:, end) == i), 😃:提取当前类别的数据。
  • mid_size:当前类别的样本数量。
  • mid_train_size:当前类别训练集的样本数量,通过将该类别的总样本数乘以训练集比例并四舍五入得到。
  • P_trainT_train:将当前类别的训练集输入和输出数据添加到训练集存储变量中。
  • P_testT_test:将当前类别的测试集输入和输出数据添加到测试集存储变量中。

通过逐类别划分数据集,确保训练集和测试集在每个类别中都有代表性,避免类别不平衡问题。

6. 数据转置
P_train = P_train'; P_test = P_test';  % 转置输入数据,使每列为一个样本
T_train = T_train'; T_test = T_test';  % 转置输出数据,使每列为一个样本
  • P_trainP_test:将输入数据矩阵转置,使每列为一个样本,符合后续模型输入的要求。
  • T_trainT_test:将输出数据矩阵转置,使每列为一个样本,符合后续模型输出的要求。
7. 得到训练集和测试样本个数
M = size(P_train, 2);  % 训练集样本数
N = size(P_test , 2);  % 测试集样本数
  • M:获取训练集的样本数量。
  • N:获取测试集的样本数量。
8. 数据归一化
[P_train, ps_input] = mapminmax(P_train, 0, 1);  % 对训练集输入特征进行归一化,范围[0,1]
P_test  = mapminmax('apply', P_test, ps_input);  % 使用训练集的归一化参数对测试集输入特征进行归一化

t_train = categorical(T_train)';  % 将训练集输出数据转换为分类类型,并转置
t_test  = categorical(T_test )';  % 将测试集输出数据转换为分类类型,并转置
  • mapminmax:使用mapminmax函数将数据缩放到指定的范围内,这里设定为[0,1]。
    • [P_train, ps_input] = mapminmax(P_train, 0, 1):对训练集输入特征进行归一化,并保存归一化参数ps_input
    • P_test = mapminmax(‘apply’, P_test, ps_input):使用训练集的归一化参数对测试集输入特征进行归一化,确保训练集和测试集的数据尺度一致。
  • categorical:将输出数据转换为分类类型,适应分类任务的需求。
    • t_train = categorical(T_train)':将训练集输出数据转换为分类类型,并转置。
    • t_test = categorical(T_test )':将测试集输出数据转换为分类类型,并转置。
9. 数据平铺
% 将数据平铺为1维数据(可选择平铺为2维或3维数据,需调整模型结构)
P_train = double(reshape(P_train, num_dim, 1, 1, M));  % 训练集数据平铺为4维数组 (特征维度 × 1 × 1 × 样本数)
P_test  = double(reshape(P_test , num_dim, 1, 1, N));  % 测试集数据平铺为4维数组 (特征维度 × 1 × 1 × 样本数)
  • reshape:将输入数据矩阵重新排列为适合LSTM网络输入的4维数组格式。
    • P_train = double(reshape(P_train, num_dim, 1, 1, M)):将训练集输入数据平铺为4维数组,其中第1维为特征维度,第4维为样本数。
    • P_test = double(reshape(P_test , num_dim, 1, 1, N)):将测试集输入数据平铺为4维数组,其中第1维为特征维度,第4维为样本数。
10. 数据格式转换
% 将数据按样本重新整理为单元格数组,适应trainNetwork函数的输入要求
for i = 1 : M
    p_train{i, 1} = P_train(:, :, 1, i);  % 训练集数据存储,每个单元格包含一个样本的特征向量
end

for i = 1 : N
    p_test{i, 1}  = P_test(:, :, 1, i);  % 测试集数据存储,每个单元格包含一个样本的特征向量
end
  • 单元格数组:将训练集和测试集的输入数据按样本存储在单元格数组中,符合trainNetwork函数的输入要求。
    • p_train{i, 1} = P_train(:, :, 1, i):将第i个训练样本的特征向量存储在单元格数组p_train的第i个单元格中。
    • p_test{i, 1} = P_test(:, :, 1, i):将第i个测试样本的特征向量存储在单元格数组p_test的第i个单元格中。
11. 建立LSTM网络模型
layers = [
    sequenceInputLayer(num_dim)  % 输入层,输入数据的维度是特征数
    
    lstmLayer(6, 'OutputMode', 'last')  % LSTM层,包含6个LSTM单元,输出最后一个时间步的结果
    reluLayer                         % ReLU激活层,增加网络的非线性
    
    fullyConnectedLayer(num_class)     % 全连接层,输出为类别数
    softmaxLayer                      % Softmax层,将输出转换为概率分布
    classificationLayer];              % 分类层,计算损失并进行分类
  • sequenceInputLayer(num_dim):定义序列输入层,输入数据的特征维度为num_dim
  • lstmLayer(6, ‘OutputMode’, ‘last’):定义LSTM层,包含6个LSTM单元,输出最后一个时间步的结果。'OutputMode', 'last'表示只输出序列的最后一个时间步的结果,适用于分类任务。
  • reluLayer:添加ReLU激活层,增加网络的非线性能力。
  • fullyConnectedLayer(num_class):添加全连接层,输出节点数量等于类别数,用于生成每个类别的得分。
  • softmaxLayer:添加Softmax层,将全连接层的输出转换为概率分布,便于分类。
  • classificationLayer:添加分类层,计算交叉熵损失并进行分类。
12. 参数设置
options = trainingOptions('adam', ...      % 选择Adam优化算法
    'MaxEpochs', 1000, ...                 % 最大训练迭代次数设为1000
    'InitialLearnRate', 0.01, ...          % 初始学习率设为0.01
    'LearnRateSchedule', 'piecewise', ...  % 学习率下降策略设为分段下降
    'LearnRateDropFactor', 0.1, ...        % 学习率下降因子设为0.1
    'LearnRateDropPeriod', 750, ...        % 每750次迭代后学习率下降
    'Shuffle', 'every-epoch', ...          % 每个epoch结束后打乱数据集
    'ValidationPatience', Inf, ...         % 关闭验证,即不进行验证
    'L2Regularization', 1e-4, ...          % L2正则化参数设为1e-4,防止过拟合
    'Plots', 'training-progress', ...      % 绘制训练过程的进度图
    'Verbose', false);                     % 关闭训练过程中的详细信息显示
  • trainingOptions:设置训练参数,选择Adam优化算法,并设定其他训练相关参数。
    • ‘adam’:选择Adam优化算法。
    • ‘MaxEpochs’, 1000:设定最大训练迭代次数为1000。
    • ‘InitialLearnRate’, 0.01:设定初始学习率为0.01。
    • ‘LearnRateSchedule’, ‘piecewise’:设定学习率下降策略为分段下降。
    • ‘LearnRateDropFactor’, 0.1:设定学习率下降因子为0.1,即学习率每次下降为之前的10%。
    • ‘LearnRateDropPeriod’, 750:设定学习率下降的周期为750次迭代。
    • ‘Shuffle’, ‘every-epoch’:设定每个epoch结束后打乱数据集顺序,增加模型的泛化能力。
    • ‘ValidationPatience’, Inf:关闭验证,即不进行验证,避免在训练过程中进行验证集的评估。
    • ‘L2Regularization’, 1e-4:设定L2正则化参数为1e-4,防止模型过拟合。
    • ‘Plots’, ‘training-progress’:启用训练过程的进度图,实时监控训练状态。
    • ‘Verbose’, false:关闭训练过程中的详细信息显示,减少命令行输出。
13. 训练模型
net = trainNetwork(p_train, t_train, layers, options);  % 使用训练数据训练LSTM网络
  • trainNetwork:使用训练数据训练LSTM网络。
    • p_train:训练集输入数据,单元格数组格式,每个单元格包含一个样本的特征向量。
    • t_train:训练集输出数据,分类类型的向量。
    • layers:定义的网络结构,包括输入层、LSTM层、激活层、全连接层、Softmax层和分类层。
    • options:训练参数设置,包括优化算法、学习率、迭代次数等。
14. 预测模型
t_sim1 = predict(net, p_train);  % 对训练集数据进行预测,得到训练集预测结果
t_sim2 = predict(net, p_test );  % 对测试集数据进行预测,得到测试集预测结果
  • predict:使用训练好的LSTM模型对输入数据进行预测。
    • net:训练好的LSTM网络模型。
    • p_trainp_test:训练集和测试集的输入数据。
  • t_sim1t_sim2:分别存储训练集和测试集的预测结果,概率向量格式。
15. 反归一化
T_sim1 = vec2ind(t_sim1');  % 将训练集预测结果的概率向量转换为类别索引
T_sim2 = vec2ind(t_sim2');  % 将测试集预测结果的概率向量转换为类别索引
  • vec2ind:将概率向量转换为类别索引,即选择概率最大的类别作为预测结果。
    • t_sim1’t_sim2’:转置预测结果矩阵,使每行对应一个样本的概率向量。
  • T_sim1T_sim2:分别存储训练集和测试集的预测类别索引。
16. 性能评价
error1 = sum((T_sim1 == T_train)) / M * 100;  % 计算训练集的分类准确率(百分比)
error2 = sum((T_sim2 == T_test )) / N * 100;  % 计算测试集的分类准确率(百分比)
  • sum((T_sim1 == T_train)):计算训练集中预测正确的样本数量。
  • sum((T_sim2 == T_test )):计算测试集中预测正确的样本数量。
  • error1:训练集的分类准确率,百分比表示。
  • error2:测试集的分类准确率,百分比表示。
17. 绘制网络分析图
analyzeNetwork(layers);  % 可视化和分析LSTM网络的结构
  • analyzeNetwork:可视化和分析定义的神经网络结构,包括各层的连接和参数设置,帮助理解和优化网络结构。
18. 绘图
绘制训练集和测试集预测结果对比图
% 绘制训练集预测结果对比图
figure
plot(1: M, T_train, 'r-*', 1: M, T_sim1, 'b-o', 'LineWidth', 1) % 绘制训练集真实类别与预测类别的对比曲线,红色星形标记为真实值,蓝色圆形标记为预测值
legend('真实值', '预测值')                                        % 添加图例,区分真实值和预测值
xlabel('预测样本')                                                % 设置X轴标签为“预测样本”
ylabel('预测结果')                                                % 设置Y轴标签为“预测结果”
string = {'训练集预测结果对比'; ['准确率=' num2str(error1) '%']};  % 创建标题字符串,包括准确率
title(string)                                                    % 添加图形标题
grid                                                             % 显示网格,提升图形的可读性

% 绘制测试集预测结果对比图
figure
plot(1: N, T_test, 'r-*', 1: N, T_sim2, 'b-o', 'LineWidth', 1)   % 绘制测试集真实类别与预测类别的对比曲线,红色星形标记为真实值,蓝色圆形标记为预测值
legend('真实值', '预测值')                                        % 添加图例,区分真实值和预测值
xlabel('预测样本')                                                % 设置X轴标签为“预测样本”
ylabel('预测结果')                                                % 设置Y轴标签为“预测结果”
string = {'测试集预测结果对比'; ['准确率=' num2str(error2) '%']};   % 创建标题字符串,包括准确率
title(string)                                                    % 添加图形标题
grid                                                             % 显示网格,提升图形的可读性
  • figure:创建新的图形窗口。
  • plot
    • 1:M, T_train, ‘r-*’:绘制训练集真实类别的曲线,红色星形标记。
    • 1:M, T_sim1, ‘b-o’:绘制训练集预测类别的曲线,蓝色圆形标记。
  • legend(‘真实值’, ‘预测值’):添加图例,区分真实值和预测值。
  • xlabel(‘预测样本’)ylabel(‘预测结果’):设置X轴和Y轴的标签。
  • string = {‘训练集预测结果对比’; [‘准确率=’ num2str(error1) ‘%’]};:创建标题字符串,包括训练集的分类准确率。
  • title(string):设置图形标题。
  • grid:显示网格,提升图形的可读性。

测试集预测结果对比图的绘制过程与训练集类似,只是数据源和标题不同。

19. 混淆矩阵
if flag_conusion == 1
    % 绘制训练集的混淆矩阵
    figure
    cm = confusionchart(T_train, T_sim1);                % 创建训练集的混淆矩阵
    cm.Title = '训练集混淆矩阵';                             % 设置混淆矩阵标题
    cm.ColumnSummary = 'column-normalized';               % 设置列摘要为列归一化
    cm.RowSummary = 'row-normalized';                     % 设置行摘要为行归一化
    
    % 绘制测试集的混淆矩阵
    figure
    cm = confusionchart(T_test, T_sim2);                 % 创建测试集的混淆矩阵
    cm.Title = '测试集混淆矩阵';                             % 设置混淆矩阵标题
    cm.ColumnSummary = 'column-normalized';               % 设置列摘要为列归一化
    cm.RowSummary = 'row-normalized';                     % 设置行摘要为行归一化
end
  • if flag_conusion == 1:判断是否需要绘制混淆矩阵。
  • confusionchart
    • confusionchart(T_train, T_sim1):创建训练集的混淆矩阵,比较真实类别和预测类别。
    • confusionchart(T_test, T_sim2):创建测试集的混淆矩阵,比较真实类别和预测类别。
  • cm.Title:设置混淆矩阵的标题。
  • cm.ColumnSummarycm.RowSummary:设置列摘要和行摘要为归一化形式,便于比较。

混淆矩阵直观展示了分类模型在各类别上的预测性能,帮助识别模型在特定类别上的误分类情况。


代码使用注意事项

  1. 数据集格式

    • 时间序列数据:确保数据集.xlsx中的数据为符合分类任务要求的格式,通常最后一列为类别标签,其他列为特征。
    • 数据顺序:时间序列数据应按照时间顺序排列,确保数据的时间依赖关系。如果需要打乱数据集顺序,可以保留res = res(randperm(num_res), :);这一行;否则,可以将其注释掉。
  2. 参数调整

    • 延时步长(kim):通过kim = 15设定,表示使用15个历史数据点作为输入特征。根据时间序列的特性和周期性调整延时步长,步长过大可能导致模型复杂度增加,步长过小可能导致模型捕捉不到足够的时间依赖信息。
    • 预测步长(zim):通过zim = 1设定,表示预测当前点之后的1个时间点的值。根据实际需求调整预测步长,适用于单步预测或多步预测。
    • 训练集比例(num_size):通过num_size = 0.7设定,表示70%的数据用于训练,30%的数据用于测试。根据数据集大小和分布调整训练集比例,确保训练集和测试集具有代表性。
    • LSTM网络参数
      • LSTM单元数(6):通过lstmLayer(6, 'OutputMode', 'last')设定LSTM层中LSTM单元的数量。根据任务复杂度和数据特性调整LSTM单元数,增加单元数可能提升模型的拟合能力,但也可能增加过拟合风险。
      • ReLU激活层:通过reluLayer增加网络的非线性能力,帮助模型更好地拟合复杂数据。
      • 全连接层和Softmax层:通过fullyConnectedLayer(num_class)softmaxLayer实现分类任务。
    • 训练参数
      • 优化算法(adam):选择Adam优化算法,具有自适应学习率调整的优势。
      • 学习率(0.01):通过'InitialLearnRate', 0.01设定初始学习率,根据训练过程中的表现调整学习率。
      • 正则化参数(1e-4):通过'L2Regularization', 1e-4设定L2正则化参数,防止模型过拟合。
      • 学习率下降策略:通过'LearnRateSchedule', 'piecewise''LearnRateDropFactor', 0.1'LearnRateDropPeriod', 750设定学习率下降策略,帮助模型在训练后期更稳定地收敛。
  3. 环境要求

    • MATLAB版本:确保使用的MATLAB版本支持trainNetworkpredictmapminmaxconfusionchart等函数。需要安装MATLAB的Deep Learning Toolbox和Statistics and Machine Learning Toolbox。
    • 工具箱
      • Deep Learning Toolbox:支持使用LSTM相关函数,如sequenceInputLayerlstmLayertrainNetwork等。
      • Statistics and Machine Learning Toolbox:支持分类相关函数,如categoricalconfusionchart等。
  4. 性能优化

    • 数据预处理
      • 归一化:通过mapminmax函数对输入数据进行归一化,提升模型训练速度和稳定性。
      • 降维:如果输入特征过多,可以考虑使用主成分分析(PCA)等降维方法,减少特征数量,提升模型训练效率和性能。
    • 模型参数优化
      • LSTM单元数:通过调整LSTM单元数,优化模型的拟合能力和泛化能力。
      • 学习率和正则化参数:根据训练过程中的表现调整学习率和正则化参数,优化模型性能。
      • 交叉验证:使用交叉验证方法优化模型参数,提升模型的泛化能力。
  5. 结果验证

    • 混淆矩阵:通过绘制混淆矩阵,分析分类错误的具体情况,了解模型在哪些类别上表现较差。
    • 准确率:通过计算训练集和测试集的分类准确率,评估模型的分类性能。
    • 多次运行:由于LSTM模型对初始参数和数据敏感,建议多次运行模型,取平均性能指标,以获得更稳定的评估结果。
    • 模型对比:将LSTM分类模型与其他分类模型(如SVM、随机森林、BP神经网络等)进行对比,评估不同模型在相同数据集上的表现差异。
  6. 性能指标理解

    • 分类准确率:衡量模型在训练集和测试集上的分类正确率,值越高表示模型性能越好。
    • 混淆矩阵:展示模型在每个类别上的预测情况,包括真正例、假正例、真负例和假负例,有助于分析模型的分类错误类型。
    • 损失曲线:通过训练过程中的损失曲线,了解模型的训练状态,判断是否存在过拟合或欠拟合现象。
  7. 模型分析与可视化

    • 网络结构分析:通过analyzeNetwork函数可视化和分析LSTM网络的结构,了解网络各层的连接和参数设置。
    • 预测结果对比图:通过绘制训练集和测试集的真实类别与预测类别对比图,直观展示模型的分类效果。
    • 混淆矩阵:通过绘制混淆矩阵,分析模型在各类别上的预测性能,识别模型的优势和不足。
  8. 代码适应性

    • 模型参数调整:根据实际数据和任务需求,调整LSTM模型的参数(如LSTM单元数、学习率、正则化参数等),优化模型性能。
    • 数据格式匹配:确保输入数据的格式与LSTM模型的要求一致。输入数据应为单元格数组格式,每个单元格包含一个样本的特征向量。
    • 特征处理:如果输入数据包含类别特征,需先进行数值编码转换,确保所有特征均为数值型数据。

通过理解和应用上述LSTM分类模型,用户可以有效地处理各种序列数据的分类任务,充分发挥LSTM在捕捉长期依赖关系和处理复杂序列数据方面的优势,提升模型的分类准确性和泛化能力。

Logo

魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。

更多推荐