gpt4 book ai didi

regression - 理解 tf.keras 中线性回归模型调整的问题

转载 作者:行者123 更新时间:2023-12-03 17:11:31 27 4
gpt4 key购买 nike

我正在处理 Linear Regression with Synthetic Data Colab exercise ,它使用玩具数据集探索线性回归。有一个构建和训练的线性回归模型,可以调整学习率、时期和批量大小。我很难理解迭代是如何完成的,以及它如何连接到“时代”和“批量大小”。我基本上不了解实际模型是如何训练的,数据是如何处理的,迭代是如何完成的。为了理解这一点,我想通过手动计算每个步骤来遵循这一点。因此,我想获得每一步的斜率和截距系数。这样我就可以看到“计算机”使用什么样的数据,放入模型中,每次特定迭代会产生什么样的模型结果以及迭代是如何完成的。我首先尝试获得每一步的斜率和截距,但是失败了,因为只有在最后才输出斜率和截距。我修改后的代码(原始,刚刚添加:)

  print("Slope")
print(trained_weight)
print("Intercept")
print(trained_bias)
代码:
import pandas as pd
import tensorflow as tf
from matplotlib import pyplot as plt

#@title Define the functions that build and train a model
def build_model(my_learning_rate):
"""Create and compile a simple linear regression model."""
# Most simple tf.keras models are sequential.
# A sequential model contains one or more layers.
model = tf.keras.models.Sequential()

# Describe the topography of the model.
# The topography of a simple linear regression model
# is a single node in a single layer.
model.add(tf.keras.layers.Dense(units=1,
input_shape=(1,)))

# Compile the model topography into code that
# TensorFlow can efficiently execute. Configure
# training to minimize the model's mean squared error.
model.compile(optimizer=tf.keras.optimizers.RMSprop(lr=my_learning_rate),
loss="mean_squared_error",
metrics=[tf.keras.metrics.RootMeanSquaredError()])

return model


def train_model(model, feature, label, epochs, batch_size):
"""Train the model by feeding it data."""

# Feed the feature values and the label values to the
# model. The model will train for the specified number
# of epochs, gradually learning how the feature values
# relate to the label values.
history = model.fit(x=feature,
y=label,
batch_size=batch_size,
epochs=epochs)

# Gather the trained model's weight and bias.
trained_weight = model.get_weights()[0]
trained_bias = model.get_weights()[1]
print("Slope")
print(trained_weight)
print("Intercept")
print(trained_bias)
# The list of epochs is stored separately from the
# rest of history.
epochs = history.epoch

# Gather the history (a snapshot) of each epoch.
hist = pd.DataFrame(history.history)

# print(hist)
# Specifically gather the model's root mean
#squared error at each epoch.
rmse = hist["root_mean_squared_error"]

return trained_weight, trained_bias, epochs, rmse

print("Defined create_model and train_model")

#@title Define the plotting functions
def plot_the_model(trained_weight, trained_bias, feature, label):
"""Plot the trained model against the training feature and label."""

# Label the axes.
plt.xlabel("feature")
plt.ylabel("label")

# Plot the feature values vs. label values.
plt.scatter(feature, label)

# Create a red line representing the model. The red line starts
# at coordinates (x0, y0) and ends at coordinates (x1, y1).
x0 = 0
y0 = trained_bias
x1 = my_feature[-1]
y1 = trained_bias + (trained_weight * x1)
plt.plot([x0, x1], [y0, y1], c='r')

# Render the scatter plot and the red line.
plt.show()

def plot_the_loss_curve(epochs, rmse):
"""Plot the loss curve, which shows loss vs. epoch."""

plt.figure()
plt.xlabel("Epoch")
plt.ylabel("Root Mean Squared Error")

plt.plot(epochs, rmse, label="Loss")
plt.legend()
plt.ylim([rmse.min()*0.97, rmse.max()])
plt.show()

print("Defined the plot_the_model and plot_the_loss_curve functions.")

my_feature = ([1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 11.0, 12.0])
my_label = ([5.0, 8.8, 9.6, 14.2, 18.8, 19.5, 21.4, 26.8, 28.9, 32.0, 33.8, 38.2])

learning_rate=0.05
epochs=1
my_batch_size=12

my_model = build_model(learning_rate)
trained_weight, trained_bias, epochs, rmse = train_model(my_model, my_feature,
my_label, epochs,
my_batch_size)
plot_the_model(trained_weight, trained_bias, my_feature, my_label)
plot_the_loss_curve(epochs, rmse)
在我的具体情况下,我的输出是:
ex1
现在我尝试在一个简单的 excel 表中复制它并手动计算 rmse:
eso
但是,我得到 21.8 而不是 23.1?另外我的损失不是 535.48,而是 476.82
因此,我的第一个问题是:我的错误在哪里,rmse 是如何计算的?
第二个问题:如何获得每个特定迭代的 rmse?让我们考虑 epoch 为 4,batch size 为 4。
exam
这给出了 4 个时期和 3 个批次,每 4 个示例(观察)。我不明白如何使用这些迭代训练模型。那么我怎样才能得到每个回归模型的系数和rmse呢?不仅针对每个时期(所以是 4 个),而且针对每次迭代。我认为每个时代都有 3 次迭代。所以我认为总共有 12 个线性回归模型结果?我想看看这 12 个模型。在没有给出信息的情况下,起始点使用的初始值是多少,使用什么样的斜率和截距?从真正的第一点开始。我没有具体说明这一点。然后我希望能够了解每一步如何调整斜率和截距。这将来自我认为的梯度下降算法。但这将是 super 加分。对我来说更重要的是首先了解这些迭代是如何完成的,以及它们如何连接到纪元和批次。
更新:我知道初始值(斜率和截距)是随机选择的。

最佳答案

基础
问题陈述
让我们考虑一组样本 X 的线性回归模型,其中每个样本由一个特征 x 表示。作为模型训练的一部分,我们正在搜索 w.x + b 行,使得 ((w.x+b) -y )^2(平方损失)最小。对于一组数据点,我们取每个样本的均方损失平均值,也就是所谓的均方误差 (MSE)。代表权重和偏差的 wb 统称为权重。
拟合线/训练模型

  • 我们有一个封闭形式的解来解决线性回归问题,是 (X^T.X)^-1.X^T.y
  • 我们也可以使用梯度下降法来搜索最小化平方损失的权重。 tensorflow、pytorch 等框架使用梯度下降来搜索权重(称为训练)。

  • 渐变得体
    用于学习回归的梯度下降算法看起来很糟糕
    w, b = some initial value
    While model has not converged:
    y_hat = w.X + b
    error = MSE(y, y_hat)
    back propagate (BPP) error and adjust weights
    上述循环的每次运行称为一个时期。但是由于资源限制, y_haterror 和 BPP 的计算不是在完整数据集上进行的,而是将数据分成更小的批次,一次对一个批次执行上述操作。此外,我们通常会固定 epoch 的数量并监控模型是否收敛。
    w, b = some initial value
    for i in range(number_of_epochs)
    for X_batch,y_batch in get_next_batch(X, y)
    y_hat = w.X_batch + b
    error = MSE(y_batch, y_hat)
    back propagate (BPP) error and adjust weights
    批量的 Keras 实现
    假设我们想在训练时添加均方根误差来跟踪模型性能。 Keras的实现方式如下
    w, b = some initial value
    for i in range(number_of_epochs)
    all_y_hats = []
    all_ys = []
    for X_batch,y_batch in get_next_batch(X, y)
    y_hat = w.X_batch + b
    error = MSE(y_batch, y_hat)

    all_y_hats.extend(y_hat)
    all_ys.extend(y_batch)

    batch_rms_error = RMSE(all_ys, all_y_hats)

    back propagate (BPP) error and adjust weights
    正如您在上面看到的,预测是累积的,并且根据累积的预测计算 RMSE,而不是取所有先前批次 RMSE 的平均值。
    在 keras 中的实现
    现在我们的基础已经明确,让我们看看如何在 keras 中实现相同的跟踪。 keras 有回调,所以我们可以 Hook on_batch_begin 回调并累积 all_y_hatsall_ys 。在 on_batch_end 回调上,keras 为我们提供了计算出的 RMSE 。我们将使用我们累积的 RMSEall_y_hats 手动计算 all_ys 并验证它是否与 keras 计算的相同。我们还将保存权重,以便我们以后可以绘制正在学习的线。
    import numpy as np
    from sklearn.metrics import mean_squared_error
    import keras
    import matplotlib.pyplot as plt

    # Some training data
    X = np.arange(16)
    y = 0.5*X +0.2

    batch_size = 8
    all_y_hats = []
    learned_weights = []

    class CustomCallback(keras.callbacks.Callback):
    def on_batch_begin(self, batch, logs={}):
    w = self.model.layers[0].weights[0].numpy()[0][0]
    b = self.model.layers[0].weights[1].numpy()[0]
    s = batch*batch_size
    all_y_hats.extend(b + w*X[s:s+batch_size])
    learned_weights.append([w,b])

    def on_batch_end(self, batch, logs={}):
    calculated_error = np.sqrt(mean_squared_error(all_y_hats, y[:len(all_y_hats)]))
    print (f"\n Calculated: {calculated_error}, Actual: {logs['root_mean_squared_error']}")
    assert np.isclose(calculated_error, logs['root_mean_squared_error'])

    def on_epoch_end(self, batch, logs={}):
    del all_y_hats[:]


    model = keras.models.Sequential()
    model.add(keras.layers.Dense(1, input_shape=(1,)))
    model.compile(optimizer=keras.optimizers.RMSprop(lr=0.01), loss="mean_squared_error", metrics=[keras.metrics.RootMeanSquaredError()])
    # We should set shuffle=False so that we know how baches are divided
    history = model.fit(X,y, epochs=100, callbacks=[CustomCallback()], batch_size=batch_size, shuffle=False)
    输出:
    Epoch 1/100
    8/16 [==============>...............] - ETA: 0s - loss: 16.5132 - root_mean_squared_error: 4.0636
    Calculated: 4.063645694548688, Actual: 4.063645839691162

    Calculated: 8.10112834945773, Actual: 8.101128578186035
    16/16 [==============================] - 0s 3ms/step - loss: 65.6283 - root_mean_squared_error: 8.1011
    Epoch 2/100
    8/16 [==============>...............] - ETA: 0s - loss: 14.0454 - root_mean_squared_error: 3.7477
    Calculated: 3.7477213352845675, Actual: 3.7477214336395264
    -------------- truncated -----------------------
    达达!断言 assert np.isclose(calculated_error, logs['root_mean_squared_error']) 从未失败,所以我们的计算/理解是正确的。
    线
    最后,让我们根据均方误差损失绘制 BPP 算法正在调整的线。我们可以使用下面的代码来创建每个批次学习的线的 png 图像以及训练数据。
    for i, (w,b) in enumerate(learned_weights):
    plt.close()
    plt.axis([-1, 18, -1, 10])
    plt.scatter(X, y)
    plt.plot([-1,17], [-1*w+b, 17*w+b], color='green')
    plt.savefig(f'img{i+1}.png')
    下面是上面图片按照学习顺序的gif动画。
    enter image description here y = 0.5*X +5.2 学习的超平面(本例中的线)
    enter image description here

    关于regression - 理解 tf.keras 中线性回归模型调整的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62485318/

    27 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com