- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我正在开发一个神经网络系统来执行 SED fitting作为西澳大利亚大学学生奖学金项目的一部分。
我通过名为 MAGPHYS 的 SED 拟合程序创建了一组大约 20,000 次运行。 .每次运行都有我们感兴趣的 42 个输入值和 32 个输出值(系统有更多输出,但我们不需要它们)
我一直在尝试使用 Keras 神经网络包来创建一个网络来学习这个函数。
我目前的网络设计使用 4 个隐藏层,完全互连,每层之间有 30 个连接。每层都使用 TanH 激活函数。我还有一个 42 维输入层和 32 维输出层,它们都使用 TanH 激活,总共 6 层。
model = Sequential()
loss = 'mse'
optimiser = SGD(lr=0.01, momentum=0.0, decay=0, nesterov=True)
model.add(Dense(output_dim=30, input_dim=42, init='glorot_uniform', activation='tanh'))
for i in range(0, 4):
model.add(Dense(output_dim=30, input_dim=30, init='glorot_uniform', activation='tanh'))
model.add(Dense(output_dim=32, input_dim=30, init='glorot_uniform', activation='tanh'))
model.compile(loss=loss, optimizer=optimiser)
我一直在使用我的输入和输出数据的最小/最大归一化来压缩 0 和 1 之间的所有值。我使用的是随机梯度下降优化器,我已经试验了各种损失函数,例如均方误差、平均绝对误差、平均绝对百分比误差等。
主要问题是,无论我如何构建我的网络,它只会生成大约所有训练输出值的平均值的输出值。它看起来不像网络有实际上正确地学习了该函数,它只是生成平均值附近的值。更糟糕的是,我试验过的一些网络设计,尤其是那些使用线性激活函数的网络设计,将仅生成输出值的平均值,并且根本不会发生变化。
示例(对于 32 个输出之一):
Output Correct
9.42609868658 = 9.647
9.26345946681 = 9.487
9.43403506231 = 9.522
9.35685760748 = 9.792
9.20564885211 = 9.287
9.39240577382 = 8.002
请注意所有输出都在 9.2 - 9.4 左右,即使这些值非常不正确。
考虑到所有这些,是什么导致像我这样的网络产生这些平均水平附近的输出?
我可以尝试使用哪些方法来解决这个问题并创建某种网络来实际生成正确的输出?
最佳答案
除了 CAFEBABE 的评论外,我只想针对这个具体问题提出一些想法:
42 个输入特征并不是大量可用的特征。不一定可以解决,但这意味着您需要更宽的隐藏层(即更多节点),以帮助实现类/标签的可分离性。此外,20K 个观察值并不是一个大数据集。如果你能得到更多的数据,你应该。情况几乎总是如此。
如果您有最小/最大归一化的具体原因,请忽略这一点,但您可以考虑对输入进行 BatchNormalizing,这有助于提高网络准确预测的能力。这实质上允许激活的输入更接近函数的中间,而不是末端。
您应该对优化进行更多试验。例如:
rmsprop
或 adam
,或学习率。 尝试一些不同的激活函数。最近的研究包括:ReLU、ELU、PReLU、SReLU。所有在keras中可用。
还尝试包括一些正则化,以避免过度拟合。研究 Dropout 或 L2/L1
虽然拥有更深层次的模型(即更多层)通常会有所帮助,但将数据维度从 42 个特征减少到 30 个,可能会损害您分离数据的能力。尝试更大的值,例如 100、500 或 1000。
您可以尝试的示例模型如下:
# imports
from sklearn.cross_validation import train_test_split
from keras.models import Sequential
from keras.layers.core import Dense, Activation, Dropout
from keras.layers.normalization import BatchNormalization
from keras.layers.advanced_activations import ELU
# data shapes
n_obs, n_feat = 20000, 42
n_hidden = 500 # play with this, bigger tends to give better separability
n_class = 32
# instantiate model
model = Sequential()
# first layer --- input
model.add(Dense(input_dim = n_feat, output_dim = n_hidden))
model.add(BatchNormalization())
model.add(ELU())
model.add(Dropout(p=0.2)) # means that 20% of the nodes are turned off, randomly
# second layer --- hidden
model.add(Dense(input_dim = n_hidden, output_dim = n_hidden))
model.add(BatchNormalization())
model.add(ELU())
model.add(Dropout(p=0.2))
# third layer --- output
model.add(Dense(input_dim = n_hidden, output_dim = n_class))
model.add(BatchNormalization())
model.add(Activation('softmax'))
# configure optimization
model.compile(optimizer = 'rmsprop', loss = 'categorical_crossentropy', metrics = ['accuracy'])
# split your data, so you test it on validation data
X_train, X_test, Y_train, Y_test = train_test_split(data, targets)
# train your model
model.fit(X_train, Y_train, validation_data = (X_test, Y_test))
祝你好运!
关于python - 神经网络生成不正确的结果,这些结果大约是输出的平均值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34712933/
我是一名优秀的程序员,十分优秀!