今天在用NAR网络预测完波浪力之后,想用另外一个网络来对比预测效果 ,于是我就改用较简单的拟合神经网络(nftool),发现效果还不错,格式也没什么问题,就记录一下心路历程。加入了lag来进行时间序列预测,这里采用前50个时间步来作为input输入,没想到运算也挺快的,半分钟就算完了。

神经网络 拟合的置信度 神经网络拟合预测_神经网络

训练代码:

clc;
clear;
load('force_PM_LT_interp.mat')
x=interp_LT(:,2);
lag=10;    % 自回归阶数,可以理解为延迟向量,参考前十个时间步来预测下一个值。lag值越大,其预测效果越好,但运行速度会比较慢。
iinput=x; % x为原始序列(行向量)
n=length(iinput);
%准备输入和输出数据
inputs=zeros(lag,n-lag);
for i=1:n-lag
    inputs(:,i)=iinput(i:i+lag-1)';
end
targets=x(lag+1:end);
targets=targets';
%创建网络
hiddenLayerSize =20; %隐藏层神经元个数
net = fitnet(hiddenLayerSize);   
%拟合神经网络是一个只有一个隐含层的BP神经网络
% 避免过拟合,划分训练,测试和验证数据的比例
net.divideParam.trainRatio = 70/100;
net.divideParam.valRatio = 15/100;
net.divideParam.testRatio = 15/100;
%训练网络
[net,tr] = train(net,inputs,targets);
%% 根据图表判断拟合好坏
yn=net(inputs);
errors=targets-yn;
figure, ploterrcorr(errors)                      %绘制误差的自相关情况(20lags)
figure, parcorr(errors)                          %绘制偏相关情况
%[h,pValue,stat,cValue]= lbqtest(errors)         %Ljung-Box Q检验(20lags)
figure,plotresponse(con2seq(targets),con2seq(yn)) %看预测的趋势与原趋势
%figure, ploterrhist(errors)                      %误差直方图
%figure, plotperform(tr)                          %误差下降线
save('training_net.mat','net');

神经网络 拟合的置信度 神经网络拟合预测_神经网络_02

 通过误差的自相关情况可以看到数值基本都在红线区间里,表明偏差不算很大。

%% 下面预测往后预测几个时间段
fn=300;  %预测步数为fn。
f_in=iinput(1:lag);
f_out=zeros(1,fn);  %预测输出
% 利用滚动预测来进行多步预测
for i=1:fn
    f_out(i)=net(f_in);
    f_in=[f_in(2:end);f_out(i)];
end
% 画出预测图
xlswrite('C:\Users\李拓\Desktop\回来之后的工作\我的code\神经网络\main函数神经网络示例2(成功预测,待修改)\测试结果.xls', f_out','sheet9','D')
H=0.01:0.01:3.1;
H5=[interp_LT(:,2)',f_out];
plot(H,H5*1e-6,'g');
hold on;
plot(interp_LT(:,1), x*1e-6,'b');
legend('without predict','predict')
xlabel('Time (s)')
ylabel('F_{ex}(MN)');

进行插值处理:

%% 下面预测往后预测几个时间段
fn=31;  %预测步数为fn。
f_in=iinput(1:lag:100);
f_out=zeros(1,fn);  %预测输出
% 多步预测时,用下面的循环将网络输出重新输入
for i=1:fn
    f_out(i)=net(f_in);    %用f_in延迟向量预测出来的下一个时间步的值
    f_in=[f_in(2:end);f_out(i)];
end
f_out=interp1(1:31,f_out,1.1:0.1:31);
% 画出预测图
xlswrite('C:\Users\李拓\Desktop\回来之后的工作\我的code\神经网络\main函数神经网络示例2(成功预测,待修改)\测试结果.xls', f_out','sheet9','D')
H=0.01:0.01:3.1;
H5=[interp_LT(1:10,2)',f_out];
plot(H,H5*1e-6,'g');
hold on;
plot(interp_LT(:,1), x*1e-6,'b');
legend('without predict','predict')
xlabel('Time (s)')
ylabel('F_{ex}(MN)');

且应该从训练神经网络开始入手,即在训练集就进行相应的取插值,也许能够解决问题。

神经网络 拟合的置信度 神经网络拟合预测_神经网络_03

因此作为延迟向量,其也需要用到for循环去一步步往前推移,才能利用新的映射关系去得到更准确的结论。即一个延迟向量他最多就只能通过滚动预测去解决近30个(这个数量可以更改,越小越精确。但在某些实际问题中:如MPC的最优控制理论中,它不能无限小,否则在这个范围内得不出最优的控制命令,这个会在后面的文章中有提及)的预测,如果需要继续预测,就要更换延迟向量。因此在训练过程中加入i来进行延迟向量的推移。

我们首先要在神经网络训练的过程中,把数据input(i+1:10:i+100)跟数据target(100+i)对应上。在预测中,我们可以将i从r=100(跟延迟向量个数和插值宽度有关)开始,这样就可以在心里来将第一组延迟向量对应第一组数据。示意图如下:

神经网络 拟合的置信度 神经网络拟合预测_机器学习_04

实现代码如下:

%% 训练

clc;
clear;
load('force_PM_LT_interp.mat')
lag=10;    % 自回归阶数,即延迟向量。lag肯定是不能变的
% T=0:0.01:30;
x=interp_LT(:,2);  %input的个数应该跟所定的时间紧密相关定为5000,而不是跟波浪力个数相关,波浪力数据集可以很大为8000。
r=100;    %跟延迟向量个数和插值宽度有关
iinput=x(1:5001); % x为原始序列(行向量)
n=length(iinput);
%准备输入和输出数据,在训练的时候,只需要很机械的把每组延迟向量跟它的target对应好,把这个映射关系确定好,再在预测从过程中推进延迟向量即可。
inputs=zeros(lag,n-r+lag);   
for i=1:n-r+lag
    inputs(:,i)=iinput(i:10:r+i-lag)';    %将iiput中的1:10:100个变为input的第一列,2:10:101个变为input的第二列。
end
targets=x(r+1:n+10);   %第101个至第5011一共4911个。
targets=targets';
%创建网络
hiddenLayerSize =20; %隐藏层神经元个数
net = fitnet(hiddenLayerSize);   
%拟合神经网络是一个只有一个隐含层的BP神经网络,任何神经网络在拟合时都需要一个反向传播的过程,否则没有反馈就无法准确拟合数据。
% 避免过拟合,划分训练,测试和验证数据的比例
net.divideParam.trainRatio = 70/100;
net.divideParam.valRatio = 15/100;
net.divideParam.testRatio = 15/100;
%训练网络
[net,tr] = train(net,inputs,targets);

%% 预测

%% 下面用第一个延迟向量来预测后面3s时间段
load('force_PM_LT_interp.mat')
load('training_net.mat')
lag=10;    
x=interp_LT(:,2);  
iinput=x(1:5001); % x为原始序列(行向量)
fn=31;  %预测步数为fn。
f_in=iinput(1:10:100);
f_out=zeros(1,fn);  %预测输出
% 多步预测时,用下面的递归预测法将网络输出重新输入
for i=1:fn
    f_out(i)=net(f_in);    %用f_in延迟向量预测出来的下一个时间步的值
    f_in=[f_in(2:end);f_out(i)];
end
f_out=interp1(1:31,f_out,1.1:0.1:31);
% 画出预测图
% xlswrite('C:\Users\李拓\Desktop\回来之后的工作\我的code\神经网络\main函数神经网络示例2(成功预测,待修改)\测试结果.xls', f_out','sheet9','D')
H=0.01:0.01:4;
H5=[interp_LT(1:100,2)',f_out] ;%取原数据前面100个,和预测的后面300个的值组合在一起;
plot(H,H5*1e-6,'g');
hold on;
plot(interp_LT(1:401,1), x(1:401,1)*1e-6,'b');

 预测结果如下:

神经网络 拟合的置信度 神经网络拟合预测_神经网络_05

神经网络 拟合的置信度 神经网络拟合预测_机器学习_06

神经网络 拟合的置信度 神经网络拟合预测_深度学习_07

 图中绿色线为预测的波浪力,蓝色线为原始的波浪力。可以发现,图1的预测效果是最好的,所以训练神经网络一定要重复训练多几遍,把训练觉得合适的神经网络再保存下来用于预测,其结果才准确。最后说一下,由于拟合神经网络是包含了输入和输出的,因此该插值方法也适用于narx网络。