Tensorflow 是一个编程系统,使用图(graph)来表示计算任务,图(graph)中的节点称之为 op (operation),一个 op 得到 0 个或多个 Tensor,执行计算,产生 0 个或多个 Tensor。Tensor 看做是一个 n 维的数组或列表。图必须在会话(Session)里被启动。python
下图显示了Session、Graph、Tensor、Variable之间的关系 算法
在TensorFlow的官方文档中,Graph 被定义为“一些 Operation 和 Tensor 的集合”。例如咱们表达以下的一个计算的 python代码,编程
a = tf.placeholder(tf.float32)
b = tf.placeholder(tf.float32)
c = tf.placeholder(tf.float32)
d = a*b+c
e = d*2
复制代码
就会生成相应的一张图,在Tensorboard中看到的图大概以下这样。其中每个圆圈表示一个Operation(输入处为Placeholder),椭圆到椭圆的边为Tensor,箭头的指向表示了这张图Operation 输入输出 Tensor 的传递关系。 数组
会话(Session)
是TensorFlow中的一个很是重要的概念。上面提到了,在TensorFlow中的全部计算都构建在一张计算图(Graph)中,这是一种对数学运算过程的可视化方法。而会话(Session)就是负责让这个图运算起来,会话(Session)
持有并管理TensorFlow程序运行时的全部资源,例如CPU或者GPU的分配。bash
方式一:明确的调用会话的生成函数和关闭会话函数session
# 建立一个会话
sess = tf.Session()
# 使用该会话执行一个结果
sess.run(...)
# 关闭会话,释放内存
sess.close()
复制代码
调用这种方式时,要明确调用Session.close()
,以释放资源。当程序异常退出时,关闭函数就不能被执行,从而致使资源泄露。数据结构
方式二:上下文管理机制自动释放全部资源 利用with结构将须要执行的代码包裹住,建立会话,并经过上下文机制管理器管理该会话框架
with tf.Session() as sess:
sess.run(...)
# 不须要再调用"Session.close()"
# 在退出with statement时,会话关闭和资源释放已自动完成
复制代码
Tips:通常状况下推荐使用方式二使用会话函数
TensorFlow用张量这种数据结构来表示全部的数据.你能够把一个张量想象成一个n维的数组或列表.一个张量有一个静态类型和动态类型的维数.张量能够在图中的节点之间流通学习
在TensorFlow系统中,张量的维数来被描述为阶.可是张量的阶和矩阵的阶并非同一个概念.张量的阶(有时是关于如顺序或度数或者是n维)是张量维数的一个数量描述.好比,下面的张量(使用Python中list定义的)就是2阶.
t = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
复制代码
你能够认为一个二阶张量就是咱们日常所说的矩阵,一阶张量能够认为是一个向量.对于一个二阶张量你能够用语句t[i, j]来访问其中的任何元素.而对于三阶张量你能够用't[i, j, k]'来访问其中的任何元素.
阶 | 数学实例 | Python 例子 |
---|---|---|
0 | 纯量 (只有大小) | s = 483 |
1 | 向量(大小和方向) | v = [1.1, 2.2, 3.3] |
2 | 矩阵(数据表) | m = [[1, 2, 3], [4, 5, 6], [7, 8, 9]] |
3 | 3阶张量 (数据立体) | t = [[[2], [4], [6]], [[8], [10], [12]], [[14], [16], [18]]] |
n | n阶 (本身想一想看) | .... |
张量是全部深度学习框架中最核心的组件,由于后续的全部运算和优化算法都是基于张量进行的。几何代数中定义的张量是基于向量和矩阵的推广,通俗一点理解的话,咱们能够将标量视为零阶张量,矢量视为一阶张量,那么矩阵就是二阶张量。
本质也是一个tensor张量,但variable主要用于数据存储(能够理解为Java中的全局变量) Variable 用于构建一个变量,在计算图的运算过程当中,其值会一直保存到程序运行结束,而通常的tensor张量在tensorflow运行过程当中只是在计算图中流过,并不会保存下来。 所以Varibale主要用来保存tensorflow构建的一些结构中的参数,这些参数才不会随着运算的消失而消失,才能最终获得一个模型。
Tips: 全部和varible有关的操做在计算的时候都要使用session会话来控制,包括计算,打印等等。
# 2.2变量
import tensorflow as tf
# 定义一个变量 X
X=tf.Variable([1,2])
# 定义一个常量 a
a=tf.constant([3,3])
# 增长一个减法op
sub=tf.subtract(X,a)
# 增长一个加法op
add=tf.add(X,sub)
# 初始化全部变量
init=tf.global_variables_initializer()
# 定义一段会话
with tf.Session() as sess:
# 在会话中执行
sess.run(init)
print(sess.run(sub))
print(sess.run(add))
# 建立一个变量,初始化为0
state=tf.Variable(0,name='counter')
# 建立一个op,做用是使state加1
new_value=tf.add(state,1)
# 赋值op
update=tf.assign(state,new_value)
# 变量初始化
init=tf.global_variables_initializer()
# 建立一个会话
with tf.Session() as sess:
# 利用会话执行初始化操做
sess.run(init)
print(sess.run(state))
for _ in range(5):
sess.run(update)
print(sess.run(state))
复制代码
会话运行完成以后,若是咱们想查看会话运行的结果,能够使用fetch来实现
import tensorflow as tf
# Fetch
# 建立三个常量
input1 = tf.constant(3.0)
input2 = tf.constant(2.0)
input3 = tf.constant(5.0)
# 执行加法和乘法操做
add=tf.add(input2,input3)
mul=tf.multiply(input1,add)
# 建立会话执行
with tf.Session() as sess:
result=sess.run([mul,add])
print(result)
复制代码
运行结果为:
[21.0, 7.0]
复制代码
当咱们构建一个模型的时候,有时候咱们须要在运行时候输入一些初始数据,这个时候定义模型数据输入在tensorflow中就是用placeholder(占位符)来完成。它的定义以下:
def placeholder(dtype, shape=None, name=None):
复制代码
其中dtype表示数据类型,shape表示维度,name表示名称。它支持单个数值与任意维度的数组输入。 1. 单个数值占位符定义
a = tf.placeholder(tf.float32)
b = tf.placeholder(tf.float32)
c = tf.add(a, b)
复制代码
当咱们须要执行获得c的运行结果时候咱们就须要在会话运行时候,经过feed来插入a与b对应的值,代码演示以下:
with tf.Session() as sess:
result = sess.run(c, feed_dict={a:3, b:4})
print(result)
复制代码
其中 feed_dict就是完成了feed数据功能,feed中文有喂饭的意思,这里仍是很形象的,对定义的模型来讲,数据就是最好的食物,因此就经过feed_dict来实现。
2. 多维数据 一样对于模型须要多维数据的状况下经过feed同样能够完成,定义二维数据的占位符,而后相加,代码以下:
_x = tf.placeholder(shape=[None, 2], dtype=tf.float32, name="x")
_y = tf.placeholder(shape=[None, 2], dtype=tf.float32, name="y")
z = tf.add(_x, _y);
复制代码
运行时候须要feed二维数组,实现以下:
with tf.Session() as sess:
result = sess.run(z, feed_dict={_x:[[3, 4], [1, 2]], _y:[[8, 8],[9, 9]]})
print(result)
复制代码
下面给出示例代码:
import tensorflow as tf
# Feed
# 常见占位符
input4=tf.placeholder(tf.float32)
input5=tf.placeholder(tf.float32)
output=tf.multiply(input4,input5)
with tf.Session() as sess:
# feed的数据以字典的形式传入
print(sess.run(output,feed_dict={input4:2.0,input5:45.2}))
复制代码
执行结果为:
90.4
复制代码
总结下,feed和fetch的做用就和他的意思是同样的,fetch用于从session中获取结果数据,feed是用于将数据喂给operation,而后用session执行。