Predict future values of a PRNN
2 views (last 30 days)
Show older comments
Dan Griffiths
on 10 Jan 2020
Commented: Asvin Kumar
on 14 Jan 2020
My data set consists of 4 input variables, and 1 target variable with 5 categories. My input and target variables are the same length (~2000 values each). I followed the tutorials with the Pattern Recognition Neural Network, and then used my data in the network with okay results. I would like to use the network to predict the next 5-20 values, but having trouble. When I use the 'sim' function, I get a matrix the size of my target (5x2200) instead of the desired size of my prediction (5x20). How do I correct the prediction error?
% Load INPUT and TARGET
Load data.mat % Contains 'inputs' & 'targets' variables
% Create a Pattern Recognition Network
hiddenLayerSize = 17;
net = patternnet(hiddenLayerSize);
% Set up Division of Data for Training, Validation, Testing
net.divideParam.trainRatio = 70/100;
net.divideParam.valRatio = 15/100;
net.divideParam.testRatio = 15/100;
% Train the Network
[net,tr] = train(net,inputs,targets);
% Test the Network
outputs = net(inputs);
errors = gsubtract(targets,outputs);
performance = perform(net,targets,outputs);
% Predict next 20 values
y = sim(net,inputs);
Any help is greatly appreciated!
Thanks,
Dan
0 Comments
Accepted Answer
Asvin Kumar
on 13 Jan 2020
Explanation for the output you’re getting:
Your patternnet is learning a mapping/relationship between the inputs and the target. Using the sim command, you’re predicting the values for every data point in inputs. Since inputs is of, I presume, size 4x2200, your predictions are of size 5x2200. Essentially, the network is predicting for every 4-length data point.
The requirement:
What you want is for the network to predict the future values. You haven’t mentioned whether there is temporal information in your dataset. That is, you haven’t mentioned whether these data points are sequential, in some sense, and have enough information among them to predict future target values. I am going to assume they do. There are, at least, two ways to achieve this.
The first way is for you train your network to predict the k-th future target which can be done with the following statement for some constant ‘k’:
[net, tr] = train(net, inputs(1:end-k), targets(1+k:end));
In this approach, you’re not learning/using any temporal relation among the datapoints. The network only learns a mapping/relation between the input for a given time instant and the target k steps into the future. This leads to the shortcoming that you’ll have to construct different networks for different values of ‘k’ if you’re constructing your networks using patternnet. You could make this better by constructing an equivalent network using fullyConnectedLayers of appropriate sizes. This has the advantage that you can drop the necessity for one-hot vectors. You can then replace the targets with a 5-20 length vectors containing the categorical target information for the next 5-20 time steps. Here’s an example to help you understand how fullyConnectedLayers are used: https://www.mathworks.com/help/deeplearning/ref/nnet.cnn.layer.fullyconnectedlayer.html#mw_bad3166a-93e7-42c0-8bd2-740cd2a842ad
The second approach is to use an LSTM. This is a type of network which can learn relations between consecutive samples. This approach can be implemented like the previous approach except it also uses temporal information. You could train the network to learn a temporal relation between the current input and a 5-20 length target vector of future categorical information. Here’s a simple example for you to model your network: https://www.mathworks.com/help/deeplearning/examples/time-series-forecasting-using-deep-learning.html
2 Comments
Asvin Kumar
on 14 Jan 2020
You can modify the targets from a one-hot representation to a single category number. You can then also create another vector of the next ‘k’ categories to be predicted for the current time point. You can do this with the following code:
[category, max_categories] = vec2ind(targets);
k = 3; % or 5 or 20 or as many future steps as you want to predict.
newtargets = fliplr(toeplitz(category(k:end),category(k:-1:1))).';
This code gives you the sequence of new targets of length k x (N-k+1) where N is the sequence length. This means you will accordingly train on a shorter sequence.
Your testing will also be different from the code given in the example. You can try using something like:
net = predictAndUpdateState(net,XTrain);
numTimeStepsTest = numel(XTest);
for i = 1:numTimeStepsTest
[net,YPred(:,i)] = predictAndUpdateState(net,XTest(:,i),'ExecutionEnvironment','cpu');
end
This way, when you predict with the patient’s data at any time point, you will get an estimate of the patient’s category in the next k time points.
More Answers (0)
See Also
Categories
Find more on Sequence and Numeric Feature Data Workflows in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!