【问题标题】:Creating Neural Network for un-encountered inputs为未遇到的输入创建神经网络
【发布时间】:2016-02-03 08:52:36
【问题描述】:

我正在使用AForge.net NN 库创建一个简单的多层前馈神经网络。我的 NN 是一个 3 层激活网络,使用反向传播学习算法通过监督学习方法进行训练。

以下是我的初始设置:

//learning rate
learningRate=0.1;

//momentum value
momentum=0;

//alpha value for bipolar sigmoid activation function
sigmoidAlphaValue=2.0;

//number of inputs to network
inputSize=5;

//number of outputs from network
predictionSize=1;

//iterations
iterations=10000;


// create multi-layer neural network
            ActivationNetwork network = new ActivationNetwork(new BipolarSigmoidFunction

(sigmoidAlphaValue), 5, 5 + 1, 3, 1);

//5 inputs
//6 neurons in input layer
//3 neurons in hidden layer
//1 neuron in output layer

// create teacher
BackPropagationLearning teacher = new BackPropagationLearning(network);

// set learning rate and momentum
teacher.LearningRate = learningRate;
teacher.Momentum = momentum;

现在我有一些看起来像这样的输入系列, 1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20

使用窗口滑动方法(如here所述)作为时间序列的输入,我的输入和

预期的输出数组看起来像这样

//Iteration #1
double input[][] = new input[0][5] {1,2,3,4,5};
double output[][] = new output[0][0] {6};

//Iteration #2
double input[][] = new input[1][5] {2,3,4,5,6};
double output[][] = new output[1][0] {7};

//Iteration #3
double input[][] = new input[2][5] {3,4,5,6,7};
double output[][] = new output[2][0] {8};
.
.
.
//Iteration #n
double input[][] = new input[n][5] {15,16,17,18,19};
double output[][] = new output[n][0] {20};

在这样使用 10k 次迭代之后

teacher.RunEpoch(input, output);

我的网络已针对给定的训练集成功训练。所以现在,如果我使用输入作为 4、5、6、7、8 进行计算,网络会成功给出 9 作为答案!

但是,当输入为 21、22、23、24、25 时,NN 无法生成 26!

我的问题: 我如何训练我的网络接受这种前所未有的输入,以产生正确的序列模式,就像在学习期间在训练集中找到的那样?

【问题讨论】:

  • 您的网络似乎过拟合了,也就是说,除了重现数据之外,它并没有真正学到任何东西。尝试减少迭代并尝试使用参数。另外,输入层中额外的 +1 单元是什么?
  • 我假设添加一个额外的输入神经元意味着它是一个偏置神经元,我的错。
  • 另外,把它放在上下文中。时间序列预测通常使用 RNN 而不是 MLP 完成。但是,如果输入是静态的,那么它应该可以与 MLP 一起使用。

标签: machine-learning neural-network time-series aforge supervised-learning


【解决方案1】:

正如@runDOSrun 所说,您的模型似乎过度拟合(训练)数据。为了避免这个问题,您可以将您的集合(时间序列)分成 3 个部分。

训练集

第一个可能是您刚刚训练网络的训练集。

验证集

第二个是验证集,对于每个训练阶段,您在验证集上测试神经网络并获取错误并将此错误存储在一个变量和神经网络的副本(克隆)中。在下一个 epoch,您必须测试(修改后的)神经网络,如果验证集上的新错误低于您上次测试的错误,则存储一个新的“验证神经网络”。它将为您提供一个神经网络,该网络可以更好地在不是训练集的集合中泛化。所以你避免过度拟合训练集。

在训练结束时,您有两个神经网络。 训练神经网络是最适合训练集的神经网络,验证神经网络,可以为您提供一个从训练集中更好地泛化的神经网络。

测试集

最后一部分,您只需在一个看不见的集合中测试您的模型并检查错误。测试集的建议是检查神经网络在看不见的测试中的行为。真正的考验。

一般来说,您可以将整个集合分成 3 个相等的部分,或者作为样本

  • 60% 用于培训
  • 20% 用于验证
  • 20% 用于测试

示例如下图:

伪代码示例,说明如何实现它:

int epochs = 1;
double error = 0;
double validationError = 10000;
object validationNetwork;
do
{
    // train your network

    error = getError(trainingSet);

    //validation part...

    var currentValidationError = getError(validationSet);
    if (currentValidationError < validationError)
    {
       validationError = currentValidationError;
       validationNeuralNetwork = neuralNetwork.Clone();
    }

} while (epochs < 2000 && error < 0.001);

时间序列的交叉验证

另一方面,您也可以尝试对时间序列进行交叉验证。首先,您将您的集合分成 6 部分(或更多部分)并训练神经网络来验证模型,如下所示:

  • 1:训练 [1],验证 [2],测试 [3]
  • 2:训练 [2]、验证 [3]、测试 [4]
  • 3:训练 [3]、验证 [4]、测试 [5]
  • 4:训练 [4],验证 [5],测试 [6]

如果你愿意,你可以分成更多的部分。

【讨论】:

  • 感谢您的回复。验证模型肯定会有所帮助,但 NN 仍然无法从其训练集中找到任何东西。似乎带有监督学习的回归无法从训练集中找到任何东西。
  • 您也可以尝试进行交叉验证。我更新了我的帖子。
  • 我会接受你的回答。谢谢。然而,我发现我能够使用 Encog 而不是使用 AForge.net 来制作更好的 NN。此问题已解决。
  • 是的,Encog 是一个非常好的Machine Learning Framework。我相信 Encog 提供的结果。还有另一个工具叫做 Accord Framework,它也有很多实现机器学习的工具。 :)
猜你喜欢
  • 1970-01-01
  • 2012-03-29
  • 1970-01-01
  • 2012-10-05
  • 1970-01-01
  • 1970-01-01
  • 2017-06-13
  • 2010-10-13
相关资源
最近更新 更多