深度学习-2:tensorflow 入门以及简单的线性拟合

这篇博客介绍了TensorFlow的基础知识,包括张量(tensor)、常数节点、可输入节点(placeholder)和可变节点(Variable)。通过实例展示了如何使用TensorFlow实现简单的线性回归,并探讨了梯度下降算法在训练过程中的应用。
摘要由CSDN通过智能技术生成

摘要:

  1. 介绍 tensorflow 入门
  2. 使用 tensorflow 实现简单的线性回归

tensorflow 入门知识

参考: https://www.tensorflow.org/get_started/get_started

载入 tensorflow 的标准语句:

import tensorflow as tf

tensor

tensor 物理上的翻译是 张量。 tensor 是 tensorflow 的基本核心数据单元,tensor 可以理解为由数据组成的多维数组,维度可以是 1 维,2 维, 3 维等等。如下所示:

3 # a rank 0 tensor; this is a scalar with shape []
[1., 2., 3.] # a rank 1 tensor; this is a vector with shape [3]
[[1., 2., 3.], [4., 5., 6.]] # a rank 2 tensor; a matrix with shape [2, 3]
[[[1., 2., 3.]], [[7., 8., 9.]]] # a rank 3 tensor with shape [2, 1, 3]

tensorflow 表面意思应该就是 tensor 的流动,实际的计算中,貌似确实蕴含了这种意思。就像 tensor 就像是水流一般,按照人们规定的路线进行流动,在规定的路线上,有很多关卡,用于对 tensor 进行相应的处理,得到最终的答案。

node

tensorflow 程序可以分为两部分:

  1. 构建计算流图
  2. 运行计算流图

一个计算流图(computaional graph)由很多节点(node)组成。


这里写图片描述
图 1

图 1 所示的计算流图用于进行线性拟合。 其中包含好几种 node

常数节点 constant node

如下所示,定义了两种常数节点:

node1 = tf.constant(3.0, dtype=tf.float32)
node2 = tf.constant(4.0) # tf.float32 是默认的类型
print(node1, node2)

输出结果为:

Tensor("Const_13:0", shape=(), dtype=float32) Tensor("Const_14:0", shape=(), dtype=float32)

可以看到,两者类型是 Const,输出值为 0。并不是 3.0 和 4.0。 为什么是这样,可以理解为,这两个节点,还没被激活,所以其输出结果默认为 0。

定义了两个结点,相当于我们构建了一个计算流图,如何运行这个计算流图?需要我们在一个 Session 对象中去运行。

sess = tf.Session()
sess.run([node1, node2])
[3.0, 4.0]

上面的构建的流图单纯的定义了两个节点,现在再定义一个 node3 节点,做为两个常数节点的和:

node3 = tf.add(node1, node2)
print('node3: ', node3)
print('sess.run(node3): ', sess.run(node3))
node3:  Tensor("add_2:0", shape=(), dtype=float32)
sess.run(node3):  7.0

上面 node1-3 构成的数据流图可以表示如下:


这里写图片描述
图 2

可输入节点 placeholder

上面建立的数据流图仅仅只是将固定节点的数据相加,当我们想要变换数据的时候,则需要重新创建数据流图,显然太麻烦。 placeholder 节点可以接收外界输入。

a = tf.placeholder(tf.float32)
b = tf.placeholder(tf.float32)
print(a, b)

其输出为:

Tensor("Placeholder_6:0", dtype=float32) Tensor("Placeholder_7:0", dtype=float32)

placeholder() 初始化的时候,一定要填写数据类型,否则会报错。

adder_node = a + b # a + b 就相当于 tf.add(a, b)
add_and_triple = add_node * 3 

相当于,我们建立一个 (a+b)*3 的这样的一个式子。

print(sess.run(add_and_triple,{a:3,b:4.5}))
print(sess.run(add_and_triple,{a:[3,2,4],b:[4.5,1,3.]}))

最终程序的输出结果为:

22.5
[ 22.5   9.   21. ]

可变节点 Variable

可变节点,顾名思义,其值可以变化。

W = tf.Variable([.3], dtype=tf.float32)
b = tf.Variable([-.3], dtype=tf.float32)
x = tf.placeholder(tf.float32)
linear_model = W * x + b

其中 Wb 属于可变节点。 常数节点在调用 tf.constant 的时候已经被初始化,但是可变节点不一样, 在调用 tf.Variable 的时候,并没有被初始化,为了对所有的可变节点进行初始化,需要调用 tf.global_variables_initializer,如下所示:

init = tf.global_variables_initializer()
sess.run(init)

这样一来,才能使用初始值去初始化所有的 Variable 变量。

print(sess.run(linear_model,{x:[1,2,3,4]}))

输出的结果为:

[ 0.          0.30000001  0.60000002  0.90000004]

作为可变节点,其参数是可以变化的,如何改变可变节点的参数? 使用 tf.assign:

print('previous:', sess.run([W, b]))
fixW = tf.assign(W,[1.])
fixb = tf.assign(b,[-1.])
sess.run([fixW, fixb])
print('late:', sess.run([W, b]))
previous: [array([ 0.30000001], dtype=float32), array([-0.30000001], dtype=float32)]

late: [array([ 1.], dtype=float32), array([-1.], dtype=float32)]

使用 tensorflow 进行线性拟合

想想最简单的线性拟合问题:


这里写图片描述
图 3

这个问题,可以使用 sklearn 中的 linear_model,使用两三行的代码即可解决。在此处,我们需要使用前面介绍的几种 node 类型,结合梯度下降算法,来实现自动学习过程。

首先当然需要构造损失函数(loss functon),损失函数一般定义为,所有的输出值与理想值之差的平方和的平方根。

y = tf.placeholder(tf.float32)
squared_deltas = tf.square(linear_model - y)
loss = tf.reduce_sum(squared_deltas)

其中,y 代表了理想值。 tf.square() 将输入的 tensor 每一个元素进行平方。 tf.reduce_sum() 即对输入的 tensor 进行求和。

为了实现,学习的过程,我们需要改变参数 Wb 使得损失函数最小。在此,我们使用的是梯度下降算法。此算法对于的函数,包含在 tf.train 中。

optimizer = tf.train.GradientDescentOptimizer(0.01)
train = optimizer.minimize(loss)

然后开始训练:

sess.run(init) # 将所有的变量使用初始值初始化。 因为之前改过 W b 的值,运行这行程序后,其值回复原来的值
for i in range(1000):
    sess.run(train,{x:[1,2,3,4],y:[0,-1,-2,-3]})
print(sess.run([W,b]))

完整的程序(复制在参考网址):

import tensorflow as tf

# Model parameters
W = tf.Variable([.3], dtype=tf.float32)
b = tf.Variable([-.3], dtype=tf.float32)
# Model input and output
x = tf.placeholder(tf.float32)
linear_model = W * x + b
y = tf.placeholder(tf.float32)

# loss
loss = tf.reduce_sum(tf.square(linear_model - y)) # sum of the squares
# optimizer
optimizer = tf.train.GradientDescentOptimizer(0.01)
train = optimizer.minimize(loss)

# training data
x_train = [1, 2, 3, 4]
y_train = [0, -1, -2, -3]
# training loop
init = tf.global_variables_initializer()
sess = tf.Session()
sess.run(init) # reset values to wrong
for i in range(1000):
  sess.run(train, {x: x_train, y: y_train})

# evaluate training accuracy
curr_W, curr_b, curr_loss = sess.run([W, b, loss], {x: x_train, y: y_train})
print("W: %s b: %s loss: %s"%(curr_W, curr_b, curr_loss))

此程序的运行结果是:

W: [-0.9999969] b: [ 0.99999082] loss: 5.69997e-11

现在,我们使用这个程序,来训练我们在图 3 中黑点所示的数据,修改程序如下:

import tensorflow as tf
import numpy as np
import matplotlib.pyplot as plt

# Model parameters
W = tf.Variable([0.], dtype=tf.float32)
b = tf.Variable([0.], dtype=tf.float32)
# Model input and output
x = tf.placeholder(tf.float32)
linear_model = W * x + b
y = tf.placeholder(tf.float32)

# loss
loss = tf.reduce_sum(tf.square(linear_model - y)) # sum of the squares
# optimizer
optimizer = tf.train.GradientDescentOptimizer(0.01)
train = optimizer.minimize(loss)

# training data
x_train = np.array([ 0.07786339,-0.03961813, 0.01103904,-0.04069594,
   -0.03422907,0.00564998,0.08864151,-0.03315126,-0.05686312,
   -0.03099563,0.05522933,-0.06009656,0.00133873,-0.02345095,
   -0.07410811,0.01966154,-0.01590626,-0.01590626,0.03906215,
   -0.0730303 ])

y_train = np.array([ 233.,   91.,  111.,  152.,  120.,   67.,  310.,   94.,  183.,
     66.,  173.,   72.,   49.,   64.,   48.,  178.,  104.,  132.,
    220.,   57.])
# training loop

init = tf.global_variables_initializer()
sess = tf.Session()
sess.run(init) # reset values to wrong
for i in range(1000):
  sess.run(train, {x: x_train, y: y_train})

# evaluate training accuracy
curr_W, curr_b, curr_loss = sess.run([W, b, loss], {x: x_train, y: y_train})
print("W: %s b: %s loss: %s"%(curr_W, curr_b, curr_loss))

#-------------plot the result--------------------
plt.scatter(x_train,y_train)
y = curr_W[0] * x_train + curr_b[0]
plt.plot(x_train, y, color='red')
plt.show()

得到结果如下:

================== RESTART: C:/Users/wangs0622/Desktop/2.py ==================
W: [ 639.07635498] b: [ 132.56671143] loss: 53342.9


这里写图片描述
图 4

直觉告诉我们, 图 3 应该比图 4 更加贴合一点。可以看出来,单纯的以输出值与理想值的差的平方和为损失函数,貌似并不是最好的选择。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值