tensorflow学习笔记 | 02 - 线性回归问题Numpy实战
Posted Mculover666
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了tensorflow学习笔记 | 02 - 线性回归问题Numpy实战相关的知识,希望对你有一定的参考价值。
一、引言
机器学习的目标是希望从已有数据中学习到一些高层次的规律,从而在给定某个新的 x 时,根据机器学习的结果,可以给出一个预测的y。
结果y通常有两种类型:连续型变量和离散型变量,对于连续型变量进行预测则使用回归模型,对于离散型变量进行预测则使用分类模型。
本文中讲述的是一个简单的线性回归问题,就是连续值预测的问题。
连续值预测的问题总结为如下:
f
θ
:
x
→
y
f_\\theta:x\\rightarrowy
fθ:x→y
其中
x
x
x 是给定的输入数据,
θ
\\theta
θ是模型的参数,
y
y
y是真实的实际结果,我们希望模型给出的预测结果
f
(
x
)
f(x)
f(x)能够完美的逼近于实际结果
y
y
y,而预测结果与实际结果之间的差值成为误差。
二、一元线性回归
1. 建立模型
二元一次方程如下:
y
=
w
∗
x
+
b
y=w*x+b
y=w∗x+b
在数学世界中,只需要给定该直线上的两个点,我们就能精确的求解出 w 和 b 的值,比如给定(1,1.567)、(2,3.043),运用小学二年级的知识,求解出 w = 1.476,b = 0.091,多么完美。
但现实世界中并非如此精确且完美,我们采集出的数据如下图所示:
对于这堆数据,因为只是一部分数据,所以可以用一次方程建模,二次方程建模,也可以用三次方程建模,这其中最简单的就是用一条直线,也就是二元一次方程建模。并且,无论取哪条直线,都不能完美的覆盖这些点,所以这个时候我们能做的,只是建立一个直线模型,如下图蓝色线:
直线模型建立完成后,在某个给定的x处,实际y值偏离直线上的y值的距离,可以理解为噪声,所以在我们最初的直线模型中加入一个噪声参数
ϵ
\\epsilon
ϵ,通常这个噪声值符合某种概率分布,在我们可以接受的范围内。:
y
=
w
∗
x
+
b
+
ϵ
y=w*x+b+\\epsilon
y=w∗x+b+ϵ
接下来,我们利用给出的足够多的真实点,去计算出
w
w
w、
b
b
b、
ϵ
\\epsilon
ϵ这三个参数的值,从而找到最接近精确解的那条直线,这就是 machine learning 要做的事情。
2. 参数求解
当我们求解出一条直线后,对于数据中的每个点都计算出误差,再将所有的相加,就可以量化出拟合的直线和实际之间的误差。
构造一个损失函数:
l
o
s
s
=
Σ
i
(
w
∗
x
i
+
b
−
y
i
)
2
loss=\\Sigma_i(w*x_i+b-yi)^2
loss=Σi(w∗xi+b−yi)2
损失函数的值越小,说明直线越接近实际值,损失函数的最小值即是最优解。
参数的最优解记为
w
′
w'
w′和
b
′
b'
b′,求解公式如下:
w
′
=
w
−
l
r
∗
l
o
s
s
′
∣
w
w'=w-lr*loss'|_w
w′=w−lr∗loss′∣w
b
′
=
b
−
l
r
∗
l
o
s
s
′
∣
b
b'=b-lr*loss'|_b
b′=b−lr∗loss′∣b
三、基于numpy的实例
step1. 计算loss函数
l
o
s
s
=
Σ
i
(
w
∗
x
i
+
b
−
y
i
)
2
=
(
w
0
x
0
+
b
0
−
y
0
)
2
+
(
w
0
x
1
+
b
0
−
y
1
)
2
+
.
.
.
+
(
w
0
x
99
+
b
0
−
y
99
)
2
loss=\\Sigma_i(w*x_i+b-yi)^2=(w_0x_0+b_0-y_0)^2+(w_0x_1+b_0-y_1)^2+...+(w_0x_99+b_0-y_99)^2
loss=Σi(w∗xi+b−yi)2=(w0x0+b0−y0)2+(w0x1+b0−y1)2+...+(w0x99+b0−y99)2
w
0
w_0
w0和
b
0
b_0
b0是随机初始化的,都初始化为0即可:
w
0
=
b
0
=
0
w_0=b_0=0
w0=b0=0
随着累加过程,loss的值会变得很大,求平均:
l
o
s
s
ˉ
=
1
N
l
o
s
s
\\barloss=\\frac1Nloss
lossˉ=N1loss
实现代码如下:
# y = wx + b
def compute_error_for_line_given_points(b, w, points):
totolError = 0
for i in range(0, len(points)):
x = points[i, 0]
y = points[i, 1]
# compute mean-squared-error
totalError += (y - (w * x + b)) ** 2
# average loss for each point
return totalError / float(len(points))
step2. 计算梯度并更新
同样的loss函数,将w和b当作自变量求偏导:
l
o
s
s
=
Σ
i
(
w
∗
x
i
+
b
−
y
i
)
2
loss=\\Sigma_i(w*x_i+b-yi)^2
loss=Σi(w∗xi+b−yi)2
实现代码如下:
def step_gradient(b_current, w_current, points, learningRate):
b_gradient = 0
w_gradient = 0
N = float(len(points))
# 对于每一个点计算梯度
for i in range(0, len(points)):
x = points[i, 0]
y = points[i, 1]
# grad_b = 2(wx+b-y)
b_gradient += (2/N) * ((w_current * x + b_current) - y)
# grad_w = 2(wx+b-y)*x
w_gradient += (2 / N) * x * ((w_current * x + b_current) - y)
# update w'
new_b = b_current - (learningRate * b_gradient)
new_w = w_current - (learningRate * w_gradient)
return [new_b, new_w]
step3. 将w’赋给w,进行循环
每次将计算出的新w’值,赋给w,重新进行计算,实现代码如下:
def gradient_descent_runner(points, starting_b, starting_w, learning_rate, num_iterations):
b = starting_b
w = starting_w
# update for severval times
for i in range(num_iterations):
b, w = step_gradient(b, w, np.array(points), learning_rate)
return [b, w]
运行程序
data.csv地址:https://github.com/dragen1860/TensorFlow-2.x-Tutorials
if __name__ == '__main__':
# 加载数据文件
points = np.genfromtxt("data.csv", delimiter=",")
learning_rate = 0.0001
initial_b = 0
initial_w = 0
num_iterations = 1000
print("Starting gradient descent at b = 0, w = 1, error = 2"
.format(initial_b, initial_w,
compute_error_for_line_given_points(initial_b, initial_w, points))
)
print("Running...")
[b, w] = gradient_descent_runner(points, initial_b, initial_w, learning_rate, num_iterations)
print("After 0 iterations b = 1, w = 2, error = 3"以上是关于tensorflow学习笔记 | 02 - 线性回归问题Numpy实战的主要内容,如果未能解决你的问题,请参考以下文章
使用 Tensorflow 的线性回归预制估计器得到错误的答案