【问题标题】:Multilayer perceptron with sigmoid activation produces straight line on sin(2x) regression具有 sigmoid 激活的多层感知器在 sin(2x) 回归上产生直线
【发布时间】:2018-07-29 14:56:28
【问题描述】:

我正在尝试使用多层感知器从 sin(2x) 函数中近似噪声数据:

# Get data
datasets = gen_datasets()
# Add noise
datasets["ysin_train"] = add_noise(datasets["ysin_train"])
datasets["ysin_test"] = add_noise(datasets["ysin_test"])
# Extract wanted data
patterns_train = datasets["x_train"]
targets_train = datasets["ysin_train"]
patterns_test = datasets["x_test"]
targets_test = datasets["ysin_test"]
# Reshape to fit model
patterns_train = patterns_train.reshape(62, 1)
targets_train = targets_train.reshape(62, 1)
patterns_test = patterns_test.reshape(62, 1)
targets_test = targets_test.reshape(62, 1)

# Parameters
learning_rate = 0.001
training_epochs = 10000
batch_size = patterns_train.shape[0]
display_step = 1

# Network Parameters
n_hidden_1 = 2
n_hidden_2 = 2
n_input = 1
n_classes = 1

# tf Graph input
X = tf.placeholder("float", [None, n_input])
Y = tf.placeholder("float", [None, n_classes])

# Store layers weight & bias
weights = {
    'h1': tf.Variable(tf.random_normal([n_input, n_hidden_1])),
    'h2': tf.Variable(tf.random_normal([n_hidden_1, n_hidden_2])),
    'out': tf.Variable(tf.random_normal([n_hidden_2, n_classes]))
}
biases = {
    'b1': tf.Variable(tf.random_normal([n_hidden_1])),
    'b2': tf.Variable(tf.random_normal([n_hidden_2])),
    'out': tf.Variable(tf.random_normal([n_classes]))
}

# Create model
def multilayer_perceptron(x):
    # Hidden fully connected layer with 2 neurons
    layer_1 = tf.sigmoid(tf.add(tf.matmul(x, weights['h1']), biases['b1']))
    # Hidden fully connected layer with 2 neurons
    layer_2 = tf.sigmoid(tf.add(tf.matmul(layer_1, weights['h2']), biases['b2']))
    # Output fully connected layer
    out_layer = tf.matmul(layer_2, weights['out']) + biases['out']
    return out_layer

# Construct model
logits = multilayer_perceptron(X)

# Define loss and optimizer
loss_op = tf.reduce_mean(tf.losses.absolute_difference(labels = Y, predictions = logits, reduction=tf.losses.Reduction.NONE))
optimizer = tf.train.GradientDescentOptimizer(learning_rate=learning_rate)
train_op = optimizer.minimize(loss_op)

# Initializing the variables
init = tf.global_variables_initializer()

with tf.Session() as sess:
    sess.run(init)

    # Training Cycle
    for epoch in range(training_epochs):

        _ = sess.run(train_op, feed_dict={X: patterns_train,
                                          Y: targets_train})
        c = sess.run(loss_op, feed_dict={X: patterns_test,
                                         Y: targets_test})
        if epoch % display_step == 0:
            print("Epoch: {0: 4} cost={1:9}".format(epoch+1, c))
    print("Optimization finished!")
    outputs = sess.run(logits, feed_dict={X: patterns_test})
    print("outputs: {0}".format(outputs.T))
    plt.plot(patterns_test, outputs, "r.", label="outputs")
    plt.plot(patterns_test, targets_test, "b.", label="targets")
    plt.legend()
    plt.show()

当我在最后绘制它时,我得到一条直线,就好像我有一个线性网络一样。看剧情:

这是线性网络的正确最小化误差。但我不应该有线性投注,因为我在 multilayer_perceptron() 函数中使用了 sigmoid 函数!为什么我的网络会这样?

【问题讨论】:

  • 你的目标代表什么类?
  • 它们是 y = sin(2x) 中的连续 y 值。没有课程。它们看起来很奇怪,因为它们添加了相当多的高斯噪声。
  • 我就是这么想的。那么你是在尝试做回归任务吗?
  • 是的,没错。
  • 你的模型看起来有点奇怪。输入(标量!)似乎是信号的采样点,即从 0 开始的线性递增函数。因此,每个输入的 logit 始终 >= 0 并且渐近地增加到 1。sigmoid(3) 已经是 0.95 ,这意味着您的梯度非常小,权重更新也是如此。因此,网络并没有学到太多东西。

标签: python tensorflow machine-learning deep-learning


【解决方案1】:

tf.random_normalstddev=1.0 的默认值(用于权重和偏差初始化)是巨大。为权重尝试显式值 stddev=0.01;至于偏差,通常的做法是将它们初始化为零。

作为初始方法,我还会尝试更高的 learning_rate 0.01(或者可能不尝试 - 请参阅相关问题中的答案 here

【讨论】:

    猜你喜欢
    • 2016-02-28
    • 2013-01-08
    • 2022-12-25
    • 2018-09-20
    • 2018-05-16
    • 2019-07-30
    • 2019-10-31
    • 2017-10-07
    • 2015-02-18
    相关资源
    最近更新 更多