2016-11-30 115 views
2

我想了解如何实现神经网络。所以我做了我自己的数据集。 Xtrain是numpy.random漂浮。 Ytrain is sign(sin(1/x^3) 尝试实施神经网络给我的结果很差,精度达到30%,随机森林有100棵树给出了97%,但是我听说NN可以近似任何函数。错在我的理解?神经网络的实现

import numpy as np 
import keras 
import math 
from sklearn.ensemble import RandomForestClassifier as RF 
train = np.random.rand(100000) 
test = np.random.rand(100000) 
def g(x): 
    if math.sin(2*3.14*x) > 0: 
     if math.cos(2*3.14*x) > 0: 
      return 0 
     else: 
      return 1 
    else: 
     if math.cos(2*3.14*x) > 0: 
      return 2 
     else: 
      return 3 
def f(x): 
    x = (1/x) ** 3 
    res = [0, 0, 0, 0] 
    res[g(x)] = 1 
    return res 

ytrain = np.array([f(x) for x in train]) 
ytest = np.array([f(x) for x in test]) 
train = np.array([[x] for x in train]) 
test = np.array([[x] for x in test]) 

from keras.models import Sequential 
from keras.layers import Dense, Activation, Embedding, LSTM 

model = Sequential() 
model.add(Dense(100, input_dim=1)) 
model.add(Activation('sigmoid')) 
model.add(Dense(100)) 
model.add(Activation('sigmoid')) 
model.add(Dense(100)) 
model.add(Activation('sigmoid')) 
model.add(Dense(4)) 
model.add(Activation('softmax')) 
model.compile(optimizer='sgd', 
      loss='categorical_crossentropy', 
      metrics=['accuracy']) 

PS我尝试了很多层,激活功能,丧失功能,优化,但从来没有超过30%的准确率:(

+1

我投票结束这个问题作为题外话,因为这是关于神经网络设计的一般问题,它会在其他stackexchange网站上得到更好的回答。 stackoverflow主要是编程问题。 – rds

回答

2

我怀疑,30%的准确率是小学习率设置和小训练步设置的组合

我跑你的代码片段model.fit(train, ytrain, nb_epoch=5, batch_size=32),经过5次时代的训练后,它的准确率大约为28%。使用相同的设置,但将训练步骤增加到nb_epoch=50,损失降至〜1.157 ish,准确度提高到40%。进一步增加培训步骤应该使模型进一步趋同。除此之外,你还可以尝试配置具有较大的学习率设定的模型,可以使收敛速度快:

model.compile(loss='categorical_crossentropy', optimizer=SGD(lr=0.1, momentum=0.9, nesterov=True), metrics=['accuracy']) 

虽然要小心,不要设置学习率过大,否则你的损失可能爆炸。

编辑: 神经网络被称为具有建模极其复杂的功能的潜力,但是,模型是否实际上产生了良好的性能是一个问题,模型是如何设计,训练,以及许多其他相关问题具体应用。

+0

好的,但我们怎样才能比较40%的准确性与优化随机森林解决方案产生97%的准确性?这是什么原因? – SaveMyLife

+1

40%不是这个NN模型能够做到的最好*性能(丢失1.157,它显然没有收敛)。这是一个表现,然后它实际收敛到全球最低点(我只训练了50个时刻,表明它可以超过30%,但我没有耐心去进一步训练)。当NN模型正确调整并且实际收敛时,它有可能产生类似甚至更好的性能。 –

0

钟育光的回答是正确的,指出你可能需要更长时间或以不同的学习速度进行训练。

我会补充一点,你的网络越深,在收敛之前你需要训练的时间就越长。对于像sign(sin(1/x^3))这样一个相对简单的函数,你可能能够摆脱比你所使用的网络更小的网络。

此外,softmax可能不是最好的输出层。你只需要得到-1或1.一个单一的tanh单位看起来会好。当您想要学习有限集合上的概率分布时,通常会使用softmax。 (由于类似的原因,您可能希望将错误函数从交叉熵切换到均方差)。

尝试使用一个S形隐藏层和输出层的网络,只有一个tanh单元。然后玩弄图层大小和学习率。也许再加上第二个隐藏层,如果你只用一个就不能得到结果,但是如果没有必要,我不会感到惊讶。

附录:在这种方法中,您将使用目标函数的直接计算来代替f(x),而不是您当前使用的单热矢量。