relu函数神经网络输出0或1

时间:2019-09-26 01:40:04

标签: python machine-learning neural-network sigmoid relu

我尝试使用Sigmoid和relu函数来实现一个简单的神经网络。 使用sigmoid函数,我得到了一些不错的输出。但是当使用relu时,我得到了0或1的数组。 (我需要relu函数,因为我愿意将代码用于某些输出> 1)。

def relu(x):
return np.maximum(0,x)

def reluDerivative(x):
  x[x<=0] = 0
  x[x>0] = 1
  return x
training_inputs = np.array([[9, 0 , 1],
[7, 1, 1],
[8, 0, 1],
[5, 1, 1]
])

training_outputs = np.array([[9, 7, 8, 5]]).T

np.random.seed(1)

synaptic_weights = 2 * np.random.random((3,1)) - 1


for iteration in range(100000):

   outputs = relu(np.dot(training_inputs, synaptic_weights))


   error = training_outputs - outputs
   adjustments = error * reluDerivative(outputs)
   synaptic_weights += np.dot(training_inputs.T, adjustments )

print("output after training: \n" , outputs)

1 个答案:

答案 0 :(得分:0)

更新

(感谢包括relu和reluDerivative方法)

错误确实是在reluDerivative(x)方法中。

当您执行x[x<=0] = 0时,您正在修改给定的numpy数组。参数x不是outputs的克隆/深拷贝,它是相同的numpy数组。因此,当您修改x时,您也会同时修改outputs

我希望您能找出导致此错误的原因-但是,如果您需要进一步的说明,请告诉我。

更新2

代码看起来比上面的问题更多,而且有些棘手:

  • 如果使用调试器逐步执行代码,您会注意到,不幸的是,使用当前的随机种子(1),会对突触权重进行初始化,以便所有训练示例均产生负点积,然后,ReLU设置为零。零的梯度为零,这是使用ReLU的风险之一。如何缓解呢?

    • 好吧,您可以使用其他种子(例如seed = 10),但这不是令人满意的解决方案
    • 如果您拥有更大的训练集(例如100个而不是4个),则出现此问题的可能性将大大降低,因为所有100个结果都不太可能产生负的点积。
    • 我注意到,每个数据行中的第一项都比其余数据大得多。对数据集执行“规范化”可以避免此问题。您可以阅读有关如何标准化输入的更多信息。
    • 最后,关于ReLU的“零梯度”问题恰恰是发明“ LeakyReLU”的原因。在较大的神经网络中,规则的ReLU在市场上可能就足够了,但是在您的简单示例中,LeaklyReLU一定可以避免此问题。
  • 一旦解决了上述问题,您仍然会注意到另一个问题。误差和梯度将在几次迭代中爆炸。这是因为您尚未使用“学习率”参数来约束权重的更新率。阅读有关如何使用学习率(或alpha)参数的信息。

祝你好运!