Tensorflow一些常用基本概念与函数

来源:互联网 发布:linux网络命令 编辑:程序博客网 时间:2024/06/05 15:11

参考文献

Tensorflow一些常用基本概念与函数 http://www.cnblogs.com/wuzhitj/archive/2017/03.html

Tensorflow笔记:常用函数说明: http://blog.csdn.net/u014595019/article/details/52805444

Tensorflow一些常用基本概念与函数(1) http://blog.csdn.net/lenbow/article/details/52152766
Tensorflow一些常用基本概念与函数(2) http://blog.csdn.net/lenbow/article/details/52181159
Tensorflow一些常用基本概念与函数(3) http://blog.csdn.net/lenbow/article/details/52213105

Tensorflow一些常用基本概念与函数(4)http://blog.csdn.net/lenbow/article/details/52218551


-------------------------------------------------------------------

1、tensorflow的基本运作

为了快速的熟悉TensorFlow编程,下面从一段简单的代码开始:

import tensorflow as tf #定义‘符号’变量,也称为占位符 a = tf.placeholder("float") b = tf.placeholder("float") y = tf.mul(a, b) #构造一个op节点 sess = tf.Session()#建立会话 #运行会话,输入数据,并计算节点,同时打印结果 print sess.run(y, feed_dict={a: 3, b: 3}) # 任务完成, 关闭会话. sess.close()


其中tf.mul(a, b)函数便是tf的一个基本的算数运算,接下来介绍跟多的相关函数。

2、tf函数

TensorFlow 将图形定义转换成分布式执行的操作, 以充分利用可用的计算资源(如 CPU 或 GPU。一般你不需要显式指定使用 CPU 还是 GPU, TensorFlow 能自动检测。如果检测到 GPU, TensorFlow 会尽可能地利用找到的第一个 GPU 来执行操作.并行计算能让代价大的算法计算加速执行,TensorFlow也在实现上对复杂操作进行了有效的改进。大部分核相关的操作都是设备相关的实现,比如GPU。下面是一些重要的操作/核:
操作组操作MathsAdd, Sub, Mul, Div, Exp, Log, Greater, Less, EqualArrayConcat, Slice, Split, Constant, Rank, Shape, ShuffleMatrixMatMul, MatrixInverse, MatrixDeterminantNeuronal NetworkSoftMax, Sigmoid, ReLU, Convolution2D, MaxPoolCheckpointingSave, RestoreQueues and syncronizationsEnqueue, Dequeue, MutexAcquire, MutexReleaseFlow controlMerge, Switch, Enter, Leave, NextIteration

TensorFlow的算术操作如下:

操作描述tf.add(x, y, name=None)求和tf.sub(x, y, name=None)减法tf.mul(x, y, name=None)乘法tf.div(x, y, name=None)除法tf.mod(x, y, name=None)取模tf.abs(x, name=None)求绝对值tf.neg(x, name=None)取负 (y = -x).tf.sign(x, name=None)返回符号 y = sign(x) = -1 if x < 0; 0 if x == 0; 1 if x > 0.tf.inv(x, name=None)取反tf.square(x, name=None)计算平方 (y = x * x = x^2).tf.round(x, name=None)舍入最接近的整数
# ‘a’ is [0.9, 2.5, 2.3, -4.4]
tf.round(a) ==> [ 1.0, 3.0, 2.0, -4.0 ]tf.sqrt(x, name=None)开根号 (y = \sqrt{x} = x^{1/2}).tf.pow(x, y, name=None)幂次方
# tensor ‘x’ is [[2, 2], [3, 3]]
# tensor ‘y’ is [[8, 16], [2, 3]]
tf.pow(x, y) ==> [[256, 65536], [9, 27]]tf.exp(x, name=None)计算e的次方tf.log(x, name=None)计算log,一个输入计算e的ln,两输入以第二输入为底tf.maximum(x, y, name=None)返回最大值 (x > y ? x : y)tf.minimum(x, y, name=None)返回最小值 (x < y ? x : y)tf.cos(x, name=None)三角函数cosinetf.sin(x, name=None)三角函数sinetf.tan(x, name=None)三角函数tantf.atan(x, name=None)三角函数ctan

张量操作Tensor Transformations

  • 数据类型转换Casting
操作描述tf.string_to_number
(string_tensor, out_type=None, name=None)字符串转为数字tf.to_double(x, name=’ToDouble’)转为64位浮点类型–float64tf.to_float(x, name=’ToFloat’)转为32位浮点类型–float32tf.to_int32(x, name=’ToInt32’)转为32位整型–int32tf.to_int64(x, name=’ToInt64’)转为64位整型–int64tf.cast(x, dtype, name=None)将x或者x.values转换为dtype
# tensor a is [1.8, 2.2], dtype=tf.float
tf.cast(a, tf.int32) ==> [1, 2] # dtype=tf.int32  
  • 形状操作Shapes and Shaping
操作描述tf.shape(input, name=None)返回数据的shape
# ‘t’ is [[[1, 1, 1], [2, 2, 2]], [[3, 3, 3], [4, 4, 4]]]
shape(t) ==> [2, 2, 3]tf.size(input, name=None)返回数据的元素数量
# ‘t’ is [[[1, 1, 1], [2, 2, 2]], [[3, 3, 3], [4, 4, 4]]]]
size(t) ==> 12tf.rank(input, name=None)返回tensor的rank
注意:此rank不同于矩阵的rank,
tensor的rank表示一个tensor需要的索引数目来唯一表示任何一个元素
也就是通常所说的 “order”, “degree”或”ndims”
#’t’ is [[[1, 1, 1], [2, 2, 2]], [[3, 3, 3], [4, 4, 4]]]
# shape of tensor ‘t’ is [2, 2, 3]
rank(t) ==> 3tf.reshape(tensor, shape, name=None)改变tensor的形状
# tensor ‘t’ is [1, 2, 3, 4, 5, 6, 7, 8, 9]
# tensor ‘t’ has shape [9]
reshape(t, [3, 3]) ==>
[[1, 2, 3],
[4, 5, 6],
[7, 8, 9]]
#如果shape有元素[-1],表示在该维度打平至一维
# -1 将自动推导得为 9:
reshape(t, [2, -1]) ==>
[[1, 1, 1, 2, 2, 2, 3, 3, 3],
[4, 4, 4, 5, 5, 5, 6, 6, 6]]tf.expand_dims(input, dim, name=None)插入维度1进入一个tensor中
#该操作要求-1-input.dims()
# ‘t’ is a tensor of shape [2]
shape(expand_dims(t, 0)) ==> [1, 2]
shape(expand_dims(t, 1)) ==> [2, 1]
shape(expand_dims(t, -1)) ==> [2, 1] <= dim <= input.dims()
  • 切片与合并(Slicing and Joining)
操作描述tf.slice(input_, begin, size, name=None)对tensor进行切片操作
其中size[i] = input.dim_size(i) - begin[i]
该操作要求 0 <= begin[i] <= begin[i] + size[i] <= Di for i in [0, n]
#’input’ is
#[[[1, 1, 1], [2, 2, 2]],[[3, 3, 3], [4, 4, 4]],[[5, 5, 5], [6, 6, 6]]]
tf.slice(input, [1, 0, 0], [1, 1, 3]) ==> [[[3, 3, 3]]]
tf.slice(input, [1, 0, 0], [1, 2, 3]) ==>
[[[3, 3, 3],
[4, 4, 4]]]
tf.slice(input, [1, 0, 0], [2, 1, 3]) ==>
[[[3, 3, 3]],
[[5, 5, 5]]]tf.split(split_dim, num_split, value, name=’split’)沿着某一维度将tensor分离为num_split tensors
# ‘value’ is a tensor with shape [5, 30]
# Split ‘value’ into 3 tensors along dimension 1
split0, split1, split2 = tf.split(1, 3, value)
tf.shape(split0) ==> [5, 10]tf.concat(concat_dim, values, name=’concat’)沿着某一维度连结tensor
t1 = [[1, 2, 3], [4, 5, 6]]
t2 = [[7, 8, 9], [10, 11, 12]]
tf.concat(0, [t1, t2]) ==> [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12]]
tf.concat(1, [t1, t2]) ==> [[1, 2, 3, 7, 8, 9], [4, 5, 6, 10, 11, 12]]
如果想沿着tensor一新轴连结打包,那么可以:
tf.concat(axis, [tf.expand_dims(t, axis) for t in tensors])
等同于tf.pack(tensors, axis=axis)tf.pack(values, axis=0, name=’pack’)将一系列rank-R的tensor打包为一个rank-(R+1)的tensor
# ‘x’ is [1, 4], ‘y’ is [2, 5], ‘z’ is [3, 6]
pack([x, y, z]) => [[1, 4], [2, 5], [3, 6]]
# 沿着第一维pack
pack([x, y, z], axis=1) => [[1, 2, 3], [4, 5, 6]]
等价于tf.pack([x, y, z]) = np.asarray([x, y, z])tf.reverse(tensor, dims, name=None)沿着某维度进行序列反转
其中dim为列表,元素为bool型,size等于rank(tensor)
# tensor ‘t’ is
[[[[ 0, 1, 2, 3],
#[ 4, 5, 6, 7],

#[ 8, 9, 10, 11]],
#[[12, 13, 14, 15],
#[16, 17, 18, 19],
#[20, 21, 22, 23]]]]
# tensor ‘t’ shape is [1, 2, 3, 4]
# ‘dims’ is [False, False, False, True]
reverse(t, dims) ==>
[[[[ 3, 2, 1, 0],
[ 7, 6, 5, 4],
[ 11, 10, 9, 8]],
[[15, 14, 13, 12],
[19, 18, 17, 16],
[23, 22, 21, 20]]]]tf.transpose(a, perm=None, name=’transpose’)调换tensor的维度顺序
按照列表perm的维度排列调换tensor顺序,
如为定义,则perm为(n-1…0)
# ‘x’ is [[1 2 3],[4 5 6]]
tf.transpose(x) ==> [[1 4], [2 5],[3 6]]
# Equivalently
tf.transpose(x, perm=[1, 0]) ==> [[1 4],[2 5], [3 6]]tf.gather(params, indices, validate_indices=None, name=None)合并索引indices所指示params中的切片
tf.gathertf.one_hot
(indices, depth, on_value=None, off_value=None,
axis=None, dtype=None, name=None)indices = [0, 2, -1, 1]
depth = 3
on_value = 5.0
off_value = 0.0
axis = -1
#Then output is [4 x 3]:
output =
[5.0 0.0 0.0] // one_hot(0)
[0.0 0.0 5.0] // one_hot(2)
[0.0 0.0 0.0] // one_hot(-1)
[0.0 5.0 0.0] // one_hot(1)

矩阵相关运算

操作描述tf.diag(diagonal, name=None)返回一个给定对角值的对角tensor
# ‘diagonal’ is [1, 2, 3, 4]
tf.diag(diagonal) ==>
[[1, 0, 0, 0]
[0, 2, 0, 0]
[0, 0, 3, 0]
[0, 0, 0, 4]]tf.diag_part(input, name=None)功能与上面相反tf.trace(x, name=None)求一个2维tensor足迹,即对角值diagonal之和tf.transpose(a, perm=None, name=’transpose’)调换tensor的维度顺序
按照列表perm的维度排列调换tensor顺序,
如为定义,则perm为(n-1…0)
# ‘x’ is [[1 2 3],[4 5 6]]
tf.transpose(x) ==> [[1 4], [2 5],[3 6]]
# Equivalently
tf.transpose(x, perm=[1, 0]) ==> [[1 4],[2 5], [3 6]]tf.matmul(a, b, transpose_a=False,
transpose_b=False, a_is_sparse=False,
b_is_sparse=False, name=None)矩阵相乘tf.matrix_determinant(input, name=None)返回方阵的行列式tf.matrix_inverse(input, adjoint=None, name=None)求方阵的逆矩阵,adjoint为True时,计算输入共轭矩阵的逆矩阵tf.cholesky(input, name=None)对输入方阵cholesky分解,
即把一个对称正定的矩阵表示成一个下三角矩阵L和其转置的乘积的分解A=LL^Ttf.matrix_solve(matrix, rhs, adjoint=None, name=None)求解tf.matrix_solve(matrix, rhs, adjoint=None, name=None)
matrix为方阵shape为[M,M],rhs的shape为[M,K],output为[M,K]

复数操作

操作描述tf.complex(real, imag, name=None)将两实数转换为复数形式
# tensor ‘real’ is [2.25, 3.25]
# tensor imag is [4.75, 5.75]
tf.complex(real, imag) ==> [[2.25 + 4.75j], [3.25 + 5.75j]]tf.complex_abs(x, name=None)计算复数的绝对值,即长度。
# tensor ‘x’ is [[-2.25 + 4.75j], [-3.25 + 5.75j]]
tf.complex_abs(x) ==> [5.25594902, 6.60492229]tf.conj(input, name=None)计算共轭复数tf.imag(input, name=None)
tf.real(input, name=None)提取复数的虚部和实部tf.fft(input, name=None)计算一维的离散傅里叶变换,输入数据类型为complex64

归约计算(Reduction)

操作描述tf.reduce_sum(input_tensor, reduction_indices=None,
keep_dims=False, name=None)计算输入tensor元素的和,或者安照reduction_indices指定的轴进行求和
# ‘x’ is [[1, 1, 1]
# [1, 1, 1]]
tf.reduce_sum(x) ==> 6
tf.reduce_sum(x, 0) ==> [2, 2, 2]
tf.reduce_sum(x, 1) ==> [3, 3]
tf.reduce_sum(x, 1, keep_dims=True) ==> [[3], [3]]
tf.reduce_sum(x, [0, 1]) ==> 6tf.reduce_prod(input_tensor,
reduction_indices=None,
keep_dims=False, name=None)计算输入tensor元素的乘积,或者安照reduction_indices指定的轴进行求乘积tf.reduce_min(input_tensor,
reduction_indices=None,
keep_dims=False, name=None)求tensor中最小值tf.reduce_max(input_tensor,
reduction_indices=None,
keep_dims=False, name=None)求tensor中最大值tf.reduce_mean(input_tensor,
reduction_indices=None,
keep_dims=False, name=None)求tensor中平均值tf.reduce_all(input_tensor,
reduction_indices=None,
keep_dims=False, name=None)对tensor中各个元素求逻辑’与’
# ‘x’ is
# [[True, True]
# [False, False]]
tf.reduce_all(x) ==> False
tf.reduce_all(x, 0) ==> [False, False]
tf.reduce_all(x, 1) ==> [True, False]tf.reduce_any(input_tensor,
reduction_indices=None,
keep_dims=False, name=None)对tensor中各个元素求逻辑’或’tf.accumulate_n(inputs, shape=None,
tensor_dtype=None, name=None)计算一系列tensor的和
# tensor ‘a’ is [[1, 2], [3, 4]]
# tensor b is [[5, 0], [0, 6]]
tf.accumulate_n([a, b, a]) ==> [[7, 4], [6, 14]]tf.cumsum(x, axis=0, exclusive=False,
reverse=False, name=None)求累积和
tf.cumsum([a, b, c]) ==> [a, a + b, a + b + c]
tf.cumsum([a, b, c], exclusive=True) ==> [0, a, a + b]
tf.cumsum([a, b, c], reverse=True) ==> [a + b + c, b + c, c]
tf.cumsum([a, b, c], exclusive=True, reverse=True) ==> [b + c, c, 0]  

分割(Segmentation)

操作描述tf.segment_sum(data, segment_ids, name=None)根据segment_ids的分段计算各个片段的和
其中segment_ids为一个size与data第一维相同的tensor
其中id为int型数据,最大id不大于size
c = tf.constant([[1,2,3,4], [-1,-2,-3,-4], [5,6,7,8]])
tf.segment_sum(c, tf.constant([0, 0, 1]))
==>[[0 0 0 0]
[5 6 7 8]]
上面例子分为[0,1]两id,对相同id的data相应数据进行求和,
并放入结果的相应id中,
且segment_ids只升不降tf.segment_prod(data, segment_ids, name=None)根据segment_ids的分段计算各个片段的积tf.segment_min(data, segment_ids, name=None)根据segment_ids的分段计算各个片段的最小值tf.segment_max(data, segment_ids, name=None)根据segment_ids的分段计算各个片段的最大值tf.segment_mean(data, segment_ids, name=None)根据segment_ids的分段计算各个片段的平均值tf.unsorted_segment_sum(data, segment_ids,
num_segments, name=None)与tf.segment_sum函数类似,
不同在于segment_ids中id顺序可以是无序的tf.sparse_segment_sum(data, indices,
segment_ids, name=None)输入进行稀疏分割求和
c = tf.constant([[1,2,3,4], [-1,-2,-3,-4], [5,6,7,8]])
# Select two rows, one segment.
tf.sparse_segment_sum(c, tf.constant([0, 1]), tf.constant([0, 0]))
==> [[0 0 0 0]]
对原data的indices为[0,1]位置的进行分割,
并按照segment_ids的分组进行求和

序列比较与索引提取(Sequence Comparison and Indexing)

操作描述tf.argmin(input, dimension, name=None)返回input最小值的索引indextf.argmax(input, dimension, name=None)返回input最大值的索引indextf.listdiff(x, y, name=None)返回x,y中不同值的索引tf.where(input, name=None)返回bool型tensor中为True的位置
# ‘input’ tensor is
#[[True, False]
#[True, False]]
# ‘input’ 有两个’True’,那么输出两个坐标值.
# ‘input’的rank为2, 所以每个坐标为具有两个维度.
where(input) ==>
[[0, 0],
[1, 0]]tf.unique(x, name=None)返回一个元组tuple(y,idx),y为x的列表的唯一化数据列表,
idx为x数据对应y元素的index
# tensor ‘x’ is [1, 1, 2, 4, 4, 4, 7, 8, 8]
y, idx = unique(x)
y ==> [1, 2, 4, 7, 8]
idx ==> [0, 0, 1, 2, 2, 2, 3, 4, 4]tf.invert_permutation(x, name=None)置换x数据与索引的关系
# tensor x is [3, 4, 0, 2, 1]
invert_permutation(x) ==> [2, 4, 3, 0, 1]

神经网络(Neural Network)

  • 激活函数(Activation Functions)
操作描述tf.nn.relu(features, name=None)整流函数:max(features, 0)tf.nn.relu6(features, name=None)以6为阈值的整流函数:min(max(features, 0), 6)tf.nn.elu(features, name=None)elu函数,exp(features) - 1 if < 0,否则features
Exponential Linear Units (ELUs)tf.nn.softplus(features, name=None)计算softplus:log(exp(features) + 1)tf.nn.dropout(x, keep_prob,
noise_shape=None, seed=None, name=None)计算dropout,keep_prob为keep概率
noise_shape为噪声的shapetf.nn.bias_add(value, bias, data_format=None, name=None)对value加一偏置量
此函数为tf.add的特殊情况,bias仅为一维,
函数通过广播机制进行与value求和,
数据格式可以与value不同,返回为与value相同格式tf.sigmoid(x, name=None)y = 1 / (1 + exp(-x))tf.tanh(x, name=None)双曲线切线激活函数
  • 卷积函数(Convolution)
操作描述tf.nn.conv2d(input, filter, strides, padding,
use_cudnn_on_gpu=None, data_format=None, name=None)在给定的4D input与 filter下计算2D卷积
输入shape为 [batch, height, width, in_channels]tf.nn.conv3d(input, filter, strides, padding, name=None)在给定的5D input与 filter下计算3D卷积
输入shape为[batch, in_depth, in_height, in_width, in_channels]
  • 池化函数(Pooling)
操作描述tf.nn.avg_pool(value, ksize, strides, padding,
data_format=’NHWC’, name=None)平均方式池化tf.nn.max_pool(value, ksize, strides, padding,
data_format=’NHWC’, name=None)最大值方法池化tf.nn.max_pool_with_argmax(input, ksize, strides,
padding, Targmax=None, name=None)返回一个二维元组(output,argmax),最大值pooling,返回最大值及其相应的索引tf.nn.avg_pool3d(input, ksize, strides,
padding, name=None)3D平均值poolingtf.nn.max_pool3d(input, ksize, strides,
padding, name=None)3D最大值pooling
  • 数据标准化(Normalization)
操作描述tf.nn.l2_normalize(x, dim, epsilon=1e-12, name=None)对维度dim进行L2范式标准化
output = x / sqrt(max(sum(x**2), epsilon))tf.nn.sufficient_statistics(x, axes, shift=None,
keep_dims=False, name=None)计算与均值和方差有关的完全统计量
返回4维元组,*元素个数,*元素总和,*元素的平方和,*shift结果
参见算法介绍tf.nn.normalize_moments(counts, mean_ss, variance_ss, shift, name=None)基于完全统计量计算均值和方差tf.nn.moments(x, axes, shift=None,
name=None, keep_dims=False)直接计算均值与方差
  • 损失函数(Losses)
操作描述tf.nn.l2_loss(t, name=None)output = sum(t ** 2) / 2
  • 分类函数(Classification)
操作描述tf.nn.sigmoid_cross_entropy_with_logits
(logits, targets, name=None)*计算输入logits, targets的交叉熵tf.nn.softmax(logits, name=None)计算softmax
softmax[i, j] = exp(logits[i, j]) / sum_j(exp(logits[i, j]))tf.nn.log_softmax(logits, name=None)logsoftmax[i, j] = logits[i, j] - log(sum(exp(logits[i])))tf.nn.softmax_cross_entropy_with_logits
(logits, labels, name=None)计算logits和labels的softmax交叉熵
logits, labels必须为相同的shape与数据类型tf.nn.sparse_softmax_cross_entropy_with_logits
(logits, labels, name=None)计算logits和labels的softmax交叉熵tf.nn.weighted_cross_entropy_with_logits
(logits, targets, pos_weight, name=None)与sigmoid_cross_entropy_with_logits()相似,
但给正向样本损失加了权重pos_weight
  • 符号嵌入(Embeddings)
操作描述tf.nn.embedding_lookup
(params, ids, partition_strategy=’mod’,
name=None, validate_indices=True)根据索引ids查询embedding列表params中的tensor值
如果len(params) > 1,id将会安照partition_strategy策略进行分割
1、如果partition_strategy为”mod”,
id所分配到的位置为p = id % len(params)
比如有13个ids,分为5个位置,那么分配方案为:
[[0, 5, 10], [1, 6, 11], [2, 7, 12], [3, 8], [4, 9]]
2、如果partition_strategy为”div”,那么分配方案为:
[[0, 1, 2], [3, 4, 5], [6, 7, 8], [9, 10], [11, 12]]tf.nn.embedding_lookup_sparse(params,
sp_ids, sp_weights, partition_strategy=’mod’,
name=None, combiner=’mean’)对给定的ids和权重查询embedding
1、sp_ids为一个N x M的稀疏tensor,
N为batch大小,M为任意,数据类型int64
2、sp_weights的shape与sp_ids的稀疏tensor权重,
浮点类型,若为None,则权重为全’1’
  • 循环神经网络(Recurrent Neural Networks)
操作描述tf.nn.rnn(cell, inputs, initial_state=None, dtype=None,
sequence_length=None, scope=None)基于RNNCell类的实例cell建立循环神经网络tf.nn.dynamic_rnn(cell, inputs, sequence_length=None,
initial_state=None, dtype=None, parallel_iterations=None,
swap_memory=False, time_major=False, scope=None)基于RNNCell类的实例cell建立动态循环神经网络
与一般rnn不同的是,该函数会根据输入动态展开
返回(outputs,state)tf.nn.state_saving_rnn(cell, inputs, state_saver, state_name,
sequence_length=None, scope=None)可储存调试状态的RNN网络tf.nn.bidirectional_rnn(cell_fw, cell_bw, inputs,
initial_state_fw=None, initial_state_bw=None, dtype=None,
sequence_length=None, scope=None)双向RNN, 返回一个3元组tuple
(outputs, output_state_fw, output_state_bw)

tf.nn.rnn简要介绍
cell: 一个RNNCell实例
inputs: 一个shape为[batch_size, input_size]的tensor
initial_state: 为RNN的state设定初值,可选
sequence_length:制定输入的每一个序列的长度,size为[batch_size],值范围为[0, T)的int型数据
其中T为输入数据序列的长度
@
@针对输入batch中序列长度不同,所设置的动态计算机制
@对于在时间t,和batch的b行,有
(output, state)(b, t) = ? (zeros(cell.output_size), states(b, sequence_length(b) - 1)) : cell(input(b, t), state(b, t - 1))


  • 求值网络(Evaluation)
操作描述tf.nn.top_k(input, k=1, sorted=True, name=None)返回前k大的值及其对应的索引tf.nn.in_top_k(predictions, targets, k, name=None)返回判断是否targets索引的predictions相应的值
是否在在predictions前k个位置中,
返回数据类型为bool类型,len与predictions同
  • 监督候选采样网络(Candidate Sampling)

对于有巨大量的多分类与多标签模型,如果使用全连接softmax将会占用大量的时间与空间资源,所以采用候选采样方法仅使用一小部分类别与标签作为监督以加速训练。

操作描述Sampled Loss Functions tf.nn.nce_loss(weights, biases, inputs, labels, num_sampled,
num_classes, num_true=1, sampled_values=None,
remove_accidental_hits=False, partition_strategy=’mod’,
name=’nce_loss’)返回noise-contrastive的训练损失结果tf.nn.sampled_softmax_loss(weights, biases, inputs, labels,
num_sampled, num_classes, num_true=1, sampled_values=None,
remove_accidental_hits=True, partition_strategy=’mod’,
name=’sampled_softmax_loss’)返回sampled softmax的训练损失
参考- Jean et al., 2014第3部分Candidate Samplers tf.nn.uniform_candidate_sampler(true_classes, num_true,
num_sampled, unique, range_max, seed=None, name=None)通过均匀分布的采样集合
返回三元tuple
1、sampled_candidates 候选集合。
2、期望的true_classes个数,为浮点值
3、期望的sampled_candidates个数,为浮点值tf.nn.log_uniform_candidate_sampler(true_classes, num_true,
num_sampled, unique, range_max, seed=None, name=None)通过log均匀分布的采样集合,返回三元tupletf.nn.learned_unigram_candidate_sampler
(true_classes, num_true, num_sampled, unique,
range_max, seed=None, name=None)根据在训练过程中学习到的分布状况进行采样
返回三元tupletf.nn.fixed_unigram_candidate_sampler(true_classes, num_true,
num_sampled, unique, range_max, vocab_file=”,
distortion=1.0, num_reserved_ids=0, num_shards=1,
shard=0, unigrams=(), seed=None, name=None)基于所提供的基本分布进行采样

保存与恢复变量

操作描述类tf.train.Saver(Saving and Restoring Variables) tf.train.Saver.__init__(var_list=None, reshape=False,
sharded=False, max_to_keep=5,
keep_checkpoint_every_n_hours=10000.0,
name=None, restore_sequentially=False,
saver_def=None, builder=None)创建一个存储器Saver
var_list定义需要存储和恢复的变量tf.train.Saver.save(sess, save_path, global_step=None,
latest_filename=None, meta_graph_suffix=’meta’,
write_meta_graph=True)保存变量tf.train.Saver.restore(sess, save_path)恢复变量tf.train.Saver.last_checkpoints列出最近未删除的checkpoint 文件名tf.train.Saver.set_last_checkpoints(last_checkpoints)设置checkpoint文件名列表tf.train.Saver.set_last_checkpoints_with_time(last_checkpoints_with_time)设置checkpoint文件名列表和时间戳


3.1 建立图(Building Graphs)

本节主要介绍建立tensorflow图的相关类或函数

* 核心图的数据结构(Core graph data structures)

tf.Graph

操作描述class tf.Graphtensorflow中的计算以图数据流的方式表示
一个图包含一系列表示计算单元的操作对象
以及在图中流动的数据单元以tensor对象表现tf.Graph.__init__()建立一个空图tf.Graph.as_default()一个将某图设置为默认图,并返回一个上下文管理器
如果不显式添加一个默认图,系统会自动设置一个全局的默认图。
所设置的默认图,在模块范围内所定义的节点都将默认加入默认图中tf.Graph.as_graph_def
(from_version=None, add_shapes=False)返回一个图的序列化的GraphDef表示
序列化的GraphDef可以导入至另一个图中(使用 import_graph_def())
或者使用C++ Session APItf.Graph.finalize()完成图的构建,即将其设置为只读模式tf.Graph.finalized返回True,如果图被完成tf.Graph.control_dependencies(control_inputs)定义一个控制依赖,并返回一个上下文管理器
with g.control_dependencies([a, b, c]):
# `d` 和 `e` 将在 `a`, `b`, 和`c`执行完之后运行.
d = …
e = …tf.Graph.device(device_name_or_function)定义运行图所使用的设备,并返回一个上下文管理器
with g.device('/gpu:0'): ...
with g.device('/cpu:0'): ...tf.Graph.name_scope(name)为节点创建层次化的名称,并返回一个上下文管理器tf.Graph.add_to_collection(name, value)将value以name的名称存储在收集器(collection)中tf.Graph.get_collection(name, scope=None)根据name返回一个收集器中所收集的值的列表tf.Graph.as_graph_element
(obj, allow_tensor=True, allow_operation=True)返回一个图中与obj相关联的对象,为一个操作节点或者tensor数据tf.Graph.get_operation_by_name(name)根据名称返回操作节点tf.Graph.get_tensor_by_name(name)根据名称返回tensor数据tf.Graph.get_operations()返回图中的操作节点列表tf.Graph.gradient_override_map(op_type_map)用于覆盖梯度函数的上下文管理器
#class tf.Graph#tensorflow运行时需要设置默认的图g = tf.Graph()with g.as_default():  # Define operations and tensors in `g`.  c = tf.constant(30.0)  assert c.graph is g##也可以使用tf.get_default_graph()获得默认图,也可在基础上加入节点或子图c = tf.constant(4.0)assert c.graph is tf.get_default_graph()
#tf.Graph.as_default#以下两段代码功能相同#1、使用Graph.as_default():g = tf.Graph()with g.as_default():  c = tf.constant(5.0)  assert c.graph is g#2、构造和设置为默认with tf.Graph().as_default() as g:  c = tf.constant(5.0)  assert c.graph is g
#tf.Graph.control_dependencies(control_inputs)# 错误代码def my_func(pred, tensor):  t = tf.matmul(tensor, tensor)  with tf.control_dependencies([pred]):    # 乘法操作(op)没有创建在该上下文,所以没有被加入依赖控制    return t# 正确代码def my_func(pred, tensor):  with tf.control_dependencies([pred]):    # 乘法操作(op)创建在该上下文,所以被加入依赖控制中    #执行完pred之后再执行matmul    return tf.matmul(tensor, tensor)
# tf.Graph.name_scope(name)# 一个图中包含有一个名称范围的堆栈,在使用name_scope(...)之后,将压(push)新名称进栈中,#并在下文中使用该名称with tf.Graph().as_default() as g:  c = tf.constant(5.0, name="c")  assert c.op.name == "c"  c_1 = tf.constant(6.0, name="c")  assert c_1.op.name == "c_1"  # Creates a scope called "nested"  with g.name_scope("nested") as scope:    nested_c = tf.constant(10.0, name="c")    assert nested_c.op.name == "nested/c"    # Creates a nested scope called "inner".    with g.name_scope("inner"):      nested_inner_c = tf.constant(20.0, name="c")      assert nested_inner_c.op.name == "nested/inner/c"    # Create a nested scope called "inner_1".    with g.name_scope("inner"):      nested_inner_1_c = tf.constant(30.0, name="c")      assert nested_inner_1_c.op.name == "nested/inner_1/c"      # Treats `scope` as an absolute name scope, and      # switches to the "nested/" scope.      with g.name_scope(scope):        nested_d = tf.constant(40.0, name="d")        assert nested_d.op.name == "nested/d"        with g.name_scope(""):          e = tf.constant(50.0, name="e")          assert e.op.name == "e"

tf.Operation

操作描述class tf.Operation代表图中的一个节点,用于计算tensors数据
该类型将由python节点构造器产生(比如tf.matmul())
或者Graph.create_op()
例如c = tf.matmul(a, b)创建一个Operation类
为类型为”MatMul”,输入为’a’,’b’,输出为’c’的操作类tf.Operation.name操作节点(op)的名称tf.Operation.type操作节点(op)的类型,比如”MatMul”tf.Operation.inputs
tf.Operation.outputs操作节点的输入与输出tf.Operation.control_inputs操作节点的依赖tf.Operation.run(feed_dict=None, session=None)在会话(Session)中运行该操作tf.Operation.get_attr(name)获取op的属性值

tf.Tensor

操作描述class tf.Tensor表示一个由操作节点op产生的值,
TensorFlow程序使用tensor数据结构来代表所有的数据,
计算图中, 操作间传递的数据都是 tensor,一个tensor是一个符号handle,
里面并没有表示实际数据,而相当于数据流的载体tf.Tensor.dtypetensor中数据类型tf.Tensor.name该tensor名称tf.Tensor.value_index该tensor输出外op的indextf.Tensor.graph该tensor所处在的图tf.Tensor.op产生该tensor的optf.Tensor.consumers()返回使用该tensor的op列表tf.Tensor.eval(feed_dict=None, session=None)在会话中求tensor的值
需要使用with sess.as_default()或者 eval(session=sess)tf.Tensor.get_shape()返回用于表示tensor的shape的类TensorShapetf.Tensor.set_shape(shape)更新tensor的shapetf.Tensor.device设置计算该tensor的设备
#tf.Tensor.get_shape()c = tf.constant([[1.0, 2.0, 3.0], [4.0, 5.0, 6.0]])print(c.get_shape())==> TensorShape([Dimension(2), Dimension(3)])
#现在有个用于图像处理的tensor->imageprint(image.get_shape())==> TensorShape([Dimension(None), Dimension(None), Dimension(3)])# 假如我们知道数据集中图像尺寸为28 x 28,那么可以设置image.set_shape([28, 28, 3])print(image.get_shape())==> TensorShape([Dimension(28), Dimension(28), Dimension(3)])

* tensor类型(Tensor types)

tf.DType

操作描述class tf.DType数据类型主要包含
tf.float16,tf.float16,tf.float32,tf.float64,
tf.bfloat16,tf.complex64,tf.complex128,
tf.int8,tf.uint8,tf.uint16,tf.int16,tf.int32,
tf.int64,tf.bool,tf.stringtf.DType.is_compatible_with(other)判断other的数据类型是否将转变为该DTypetf.DType.name数据类型名称tf.DType.base_dtype返回该DType的基础DType,而非参考的数据类型(non-reference)tf.DType.as_ref返回一个基于DType的参考数据类型tf.DType.is_floating判断是否为浮点类型tf.DType.is_complex判断是否为复数tf.DType.is_integer判断是否为整数tf.DType.is_unsigned判断是否为无符号型数据tf.DType.as_numpy_dtype返回一个基于DType的numpy.dtype类型tf.DType.max
tf.DType.min返回这种数据类型能表示的最大值及其最小值tf.as_dtype(type_value)返回由type_value转变得的相应tf数据类型

* 通用函数(Utility functions)

操作描述tf.device(device_name_or_function)基于默认的图,其功能便为Graph.device()tf.container(container_name)基于默认的图,其功能便为Graph.container()tf.name_scope(name)基于默认的图,其功能便为 Graph.name_scope()tf.control_dependencies(control_inputs)基于默认的图,其功能便为Graph.control_dependencies()tf.convert_to_tensor
(value, dtype=None, name=None, as_ref=False)
将value转变为tensor数据类型tf.get_default_graph()返回返回当前线程的默认图tf.reset_default_graph()清除默认图的堆栈,并设置全局图为默认图tf.import_graph_def(graph_def, input_map=None,
return_elements=None, name=None, op_dict=None,
producer_op_list=None)将graph_def的图导入到python中

* 图收集(Graph collections)

操作描述tf.add_to_collection(name, value)基于默认的图,其功能便为Graph.add_to_collection()tf.get_collection(key, scope=None)基于默认的图,其功能便为Graph.get_collection()

* 定义新操作节点(Defining new operations)

tf.RegisterGradient

操作描述class tf.RegisterGradient返回一个用于寄存op类型的梯度函数的装饰器tf.NoGradient(op_type)设置操作节点类型op_type的节点没有指定的梯度class tf.RegisterShape返回一个用于寄存op类型的shape函数的装饰器class tf.TensorShape表示tensor的shapetf.TensorShape.merge_with(other)与other合并shape信息,返回一个TensorShape类tf.TensorShape.concatenate(other)与other的维度相连结tf.TensorShape.ndims返回tensor的ranktf.TensorShape.dims返回tensor的维度tf.TensorShape.as_list()以list的形式返回tensor的shapetf.TensorShape.is_compatible_with(other)判断shape是否为兼容
TensorShape(None)与其他任何shape值兼容class tf.Dimension tf.Dimension.is_compatible_with(other)判断dims是否为兼容tf.Dimension.merge_with(other)与other合并dims信息tf.op_scope(values, name, default_name=None)在python定义op时,返回一个上下文管理器
#tf.RegisterGradient#该装饰器只使用于定义一个新的op类型时候,如果一个op有m个输入,n个输出。那么该梯度函数应该设置原始的#操作类型,以及n个Tensor对象(表示每一个op输出的梯度),以及m个对象(表示每一个op输入的偏梯度)#以操作节点类型为'Sub'为例,两输入为x,y。为一个输出x-y@tf.RegisterGradient("Sub")def _sub_grad(unused_op, grad):  return grad, tf.neg(grad)
#tf.op_scope#定义一个名称为my_op的python操作节点opdef my_op(a, b, c, name=None):  with tf.op_scope([a, b, c], name, "MyOp") as scope:    a = tf.convert_to_tensor(a, name="a")    b = tf.convert_to_tensor(b, name="b")    c = tf.convert_to_tensor(c, name="c")    # Define some computation that uses `a`, `b`, and `c`.    return foo_op(..., name=scope)


3.2 输入和读取器(Inputs and Readers)

本节主要介绍tensorflow中数据的读入相关类或函数


* 占位符(Placeholders)

tf提供一种占位符操作,在执行时需要为其提供数据data。

操作描述tf.placeholder(dtype, shape=None, name=None)为一个tensor插入一个占位符
eg:x = tf.placeholder(tf.float32, shape=(1024, 1024))tf.placeholder_with_default(input, shape, name=None)当输出没有fed时,input通过一个占位符optf.sparse_placeholder(dtype, shape=None, name=None)为一个稀疏tensor插入一个占位符

* 读取器(Readers)

tf提供一系列读取各种数据格式的类。对于多文件输入,可以使用函数tf.train.string_input_producer,该函数将创建一个保持文件的FIFO队列,以供reader使用。或者如果输入的这些文件名有相雷同的字符串,也可以使用函数tf.train.match_filenames_once。

操作描述class tf.ReaderBase不同的读取器类型的基本类tf.ReaderBase.read(queue, name=None)返回下一个记录对(key, value),queue为tf文件队列FIFOQueuetf.ReaderBase.read_up_to(queue, num_records, name=None)返回reader产生的num_records对(key, value)tf.ReaderBase.reader_ref返回应用在该reader上的Optf.ReaderBase.reset(name=None)恢复reader为初始状态tf.ReaderBase.restore_state(state, name=None)恢复reader为之前的保存状态statetf.ReaderBase.serialize_state(name=None)返回一个reader解码后产生的字符串tansorclass tf.TextLineReader tf.TextLineReader.num_records_produced(name=None)返回reader已经产生的记录(records )数目tf.TextLineReader.num_work_units_completed(name=None)返回该reader已经完成的处理的work数目tf.TextLineReader.read(queue, name=None)返回reader所产生的下一个记录对 (key, value),该reader可以限定新产生输出的行数tf.TextLineReader.reader_ref返回应用在该reader上的Optf.TextLineReader.reset(name=None)恢复reader为初始状态tf.TextLineReader.restore_state(state, name=None)恢复reader为之前的保存状态statetf.TextLineReader.serialize_state(name=None)返回一个reader解码后产生的字符串tansorclass tf.WholeFileReader一个阅读器,读取整个文件,返回文件名称key,以及文件中所有的内容value,该类的方法同上,不赘述class tf.IdentityReader一个reader,以key和value的形式,输出一个work队列。该类其他方法基本同上class tf.TFRecordReader读取TFRecord格式文件的reader。该类其他方法基本同上class tf.FixedLengthRecordReader输出

* 数据转换(Converting)

tf提供一系列方法将各种格式数据转换为tensor表示。

操作描述tf.decode_csv(records, record_defaults,
field_delim=None, name=None)将csv转换为tensor,与tf.TextLineReader搭配使用tf.decode_raw(bytes, out_type,
little_endian=None, name=None)将bytes转换为一个数字向量表示,bytes为一个字符串类型的tensor
与函数 tf.FixedLengthRecordReader搭配使用,详见tf的CIFAR-10例子

选取与要输入的文件格式相匹配的reader,并将文件队列提供给reader的读方法( read method)。读方法将返回文件唯一标识的key,以及一个记录(record)(有助于对出现一些另类的records时debug),以及一个标量的字符串值。再使用一个(或多个)解码器(decoder) 或转换操作(conversion ops)将字符串转换为tensor类型。

#读取文件队列,使用reader中read的方法,返回key与valuefilename_queue = tf.train.string_input_producer(["file0.csv", "file1.csv"])reader = tf.TextLineReader()key, value = reader.read(filename_queue)record_defaults = [[1], [1], [1], [1], [1]]col1, col2, col3, col4, col5 = tf.decode_csv(    value, record_defaults=record_defaults)features = tf.pack([col1, col2, col3, col4])with tf.Session() as sess:  # Start populating the filename queue.  coord = tf.train.Coordinator()  threads = tf.train.start_queue_runners(coord=coord)  for i in range(1200):    # Retrieve a single instance:    example, label = sess.run([features, col5])  coord.request_stop()  coord.join(threads)

* Example protocol buffer

提供了一些Example protocol buffers,tf所推荐的用于训练样本的数据格式,它们包含特征信息,详情可见。
这是一种与前述将手上现有的各种数据类型转换为支持的格式的方法,这种方法更容易将网络结构与数据集融合或匹配。这种tensorflow所推荐的数据格式是一个包含tf.train.Example protocol buffers (包含特征Features域)的TFRecords文件。
1、获取这种格式的文件方式为,首先将一般的数据格式填入Example protocol buffer中,再将 protocol buffer序列化为一个字符串,然后使用tf.python_io.TFRecordWriter类的相关方法将字符串写入一个TFRecords文件中,参见MNIST例子,将MNIST 数据转换为该类型数据。
2、读取TFRecords格式文件的方法为,使用tf.TFRecordReader读取器和tf.parse_single_example解码器。parse_single_example操作将 example protocol buffers解码为tensor形式。参见MNIST例子

操作描述class tf.VarLenFeature解析变长的输入特征feature相关配置class tf.FixedLenFeature解析定长的输入特征feature相关配置class tf.FixedLenSequenceFeature序列项目中的稠密(dense )输入特征的相关配置tf.parse_example(serialized, features,
name=None, example_names=None)
将一组Example protos解析为tensor的字典形式
解析serialized所给予的序列化的一些Example protos
返回一个由特征keys映射Tensor和SparseTensor值的字典tf.parse_single_example(serialized, features,
name=None, example_names=None)
解析一个单独的Example proto,与tf.parse_example方法雷同tf.decode_json_example(json_examples, name=None)将JSON编码的样本记录转换为二进制protocol buffer字符串

#tf.parse_example的使用举例#输入序列化数据如下: serialized = [  features    { feature { key: "ft" value { float_list { value: [1.0, 2.0] } } } },  features    { feature []},  features    { feature { key: "ft" value { float_list { value: [3.0] } } }]#那么输出为一个字典(dict),如下:{"ft": SparseTensor(indices=[[0, 0], [0, 1], [2, 0]],                    values=[1.0, 2.0, 3.0],                    shape=(3, 2)) }##########再来看一个例子,给定两个序列化的原始输入样本:[  features {    feature { key: "kw" value { bytes_list { value: [ "knit", "big" ] } } }    feature { key: "gps" value { float_list { value: [] } } }  },  features {    feature { key: "kw" value { bytes_list { value: [ "emmy" ] } } }    feature { key: "dank" value { int64_list { value: [ 42 ] } } }    feature { key: "gps" value { } }  }]#相关参数如下:example_names: ["input0", "input1"],features: {    "kw": VarLenFeature(tf.string),    "dank": VarLenFeature(tf.int64),    "gps": VarLenFeature(tf.float32),}#那么有如下输出:{  "kw": SparseTensor(      indices=[[0, 0], [0, 1], [1, 0]],      values=["knit", "big", "emmy"]      shape=[2, 2]),  "dank": SparseTensor(      indices=[[1, 0]],      values=[42],      shape=[2, 1]),  "gps": SparseTensor(      indices=[],      values=[],      shape=[2, 0]),}##########对于两个样本的输出稠密结果情况[  features {    feature { key: "age" value { int64_list { value: [ 0 ] } } }    feature { key: "gender" value { bytes_list { value: [ "f" ] } } }   },   features {    feature { key: "age" value { int64_list { value: [] } } }    feature { key: "gender" value { bytes_list { value: [ "f" ] } } }  }]#我们可以使用以下参数example_names: ["input0", "input1"],features: {    "age": FixedLenFeature([], dtype=tf.int64, default_value=-1),    "gender": FixedLenFeature([], dtype=tf.string),}#期望的结果如下{  "age": [[0], [-1]],  "gender": [["f"], ["f"]],}
##Example protocol buffer相关使用的例子#将mnist的数据转换为TFRecords文件格式import osimport tensorflow as tffrom tensorflow.contrib.learn.python.learn.datasets import mnistSOURCE_URL = 'http://yann.lecun.com/exdb/mnist/'TRAIN_IMAGES = 'train-images-idx3-ubyte.gz'  # MNIST filenamesTRAIN_LABELS = 'train-labels-idx1-ubyte.gz'TEST_IMAGES = 't10k-images-idx3-ubyte.gz'TEST_LABELS = 't10k-labels-idx1-ubyte.gz'tf.app.flags.DEFINE_string('directory', '/tmp/data',                           'Directory to download data files and write the '                           'converted result')tf.app.flags.DEFINE_integer('validation_size', 5000,                            'Number of examples to separate from the training '                            'data for the validation set.')FLAGS = tf.app.flags.FLAGSdef _int64_feature(value):  return tf.train.Feature(int64_list=tf.train.Int64List(value=[value]))def _bytes_feature(value):  return tf.train.Feature(bytes_list=tf.train.BytesList(value=[value]))def convert_to(data_set, name):  images = data_set.images  labels = data_set.labels  num_examples = data_set.num_examples  if images.shape[0] != num_examples:    raise ValueError('Images size %d does not match label size %d.' %                     (images.shape[0], num_examples))  rows = images.shape[1]  cols = images.shape[2]  depth = images.shape[3]  filename = os.path.join(FLAGS.directory, name + '.tfrecords')  print('Writing', filename)  writer = tf.python_io.TFRecordWriter(filename)  for index in range(num_examples):    image_raw = images[index].tostring()    example = tf.train.Example(features=tf.train.Features(feature={        'height': _int64_feature(rows),        'width': _int64_feature(cols),        'depth': _int64_feature(depth),        'label': _int64_feature(int(labels[index])),        'image_raw': _bytes_feature(image_raw)}))    writer.write(example.SerializeToString())  writer.close()def main(argv):  # Get the data.  data_sets = mnist.read_data_sets(FLAGS.directory,                                   dtype=tf.uint8,                                   reshape=False)  # Convert to Examples and write the result to TFRecords.  convert_to(data_sets.train, 'train')  convert_to(data_sets.validation, 'validation')  convert_to(data_sets.test, 'test')if __name__ == '__main__':  tf.app.run()






4.1 数据IO {Data IO (Python functions)}

一个TFRecords 文件为一个字符串序列。这种格式并非随机获取,它比较适合大规模的数据流,而不太适合需要快速分区或其他非序列获取方式。

数据IO {Data IO (Python functions)}

操作描述class tf.python_io.TFRecordWriter一个用于将记录(records)写入TFRecords文件的类tf.python_io.TFRecordWriter.__init__(path, options=None)打开文件路径,并创建一个TFRecordWriter以供写入tf.python_io.TFRecordWriter.write(record)将一个字符串records写入文件中tf.python_io.TFRecordWriter.close()关闭文件tf.python_io.tf_record_iterator(path, options=None)从TFRecords文件中读取记录的迭代器

4.2 运行图(Running Graphs)

会话管理 (Session management)

操作描述class tf.Session运行TF操作的类,
一个Session对象将操作节点op封装在一定的环境内运行,
同时tensor对象将被计算求值tf.Session.__init__(target=”, graph=None, config=None)创建一个新的会话tf.Session.run(fetches, feed_dict=None,
options=None, run_metadata=None)运行fetches中的操作节点并求其值tf.Session.close()关闭会话tf.Session.graph返回加载值该会话的图(graph)tf.Session.as_default()设置该对象为默认会话,并返回一个上下文管理器tf.Session.reset(target, containers=None, config=None)重设target的资源容器,并关闭所有连接的会话
在0.10版本该功能仅应用在分布会话中
target:为执行引擎所连接的目标,其包含有资源容器,
该资源容器分布在同一个集群的所有works上class tf.InteractiveSession使用在交互式上下文环境的tf会话,比如shell,ipythontf.InteractiveSession.close()关闭一个InteractiveSessiontf.get_default_session()返回当前线程的默认会话

tf.Session

#一个简单的tf.Session例子# 建立一个graph.a = tf.constant(5.0)b = tf.constant(6.0)c = a * b# 将graph载入到一个会话session中sess = tf.Session()# 计算tensor `c`.print(sess.run(c))
#一个会话可能会占用一些资源,比如变量、队列和读取器(reader)。释放这些不再使用的资源非常重要。#使用close()方法关闭会话,或者使用上下文管理器,释放资源。# 使用`close()`方法.sess = tf.Session()sess.run(...)sess.close()# 使用上下文管理器with tf.Session() as sess:  sess.run(...)

tf.Session()的变量设置, ConfigProto protocol buffer为会话提供了不同的配置选项。比如,创建一个会话,对设备布局使用软约束条件,以及对分布

# Launch the graph in a session that allows soft device placement and# logs the placement decisions.sess = tf.Session(config=tf.ConfigProto(allow_soft_placement=True,                                        log_device_placement=True))

tf.Session.run

 a = tf.constant([10, 20])   b = tf.constant([1.0, 2.0])   # 'fetches' 可以为单个数   v = session.run(a)   # v is the numpy array [10, 20]   # 'fetches' 可以为一个list.   v = session.run([a, b])   # v a Python list with 2 numpy arrays: the numpy array [10, 20] and the   # 1-D array [1.0, 2.0]   # 'fetches' 可以是 lists, tuples, namedtuple, dicts中的任意:   MyData = collections.namedtuple('MyData', ['a', 'b'])   v = session.run({'k1': MyData(a, b), 'k2': [b, a]})   # v 为一个dict,并有   # v['k1'] is a MyData namedtuple with 'a' the numpy array [10, 20] and   # 'b' the numpy array [1.0, 2.0]   # v['k2'] is a list with the numpy array [1.0, 2.0] and the numpy array   # [10, 20].

tf.Session.as_default()
使用关键字with指定会话, 可以在会话中执行Operation.run()或Tensor.eval(),以得到运行的tensor结果

c = tf.constant(..)sess = tf.Session()with sess.as_default():  assert tf.get_default_session() is sess  print(c.eval())

使用函数tf.get_default_session()来得到当前默认的会话
需要注意的是,退出该as_default上下文管理器时,并没有关闭该会话(session ),必须明确的关闭会话

c = tf.constant(...)sess = tf.Session()with sess.as_default():  print(c.eval())# ...with sess.as_default():  print(c.eval())#关闭会话sess.close()#使用 with tf.Session()方式可以创建并自动关闭会话

tf.InteractiveSession

sess = tf.InteractiveSession()a = tf.constant(5.0)b = tf.constant(6.0)c = a * b# 我们直接使用'c.eval()' 而没有通过'sess'print(c.eval())sess.close()

以上的例子,在非交互会话的版本中为,

a = tf.constant(5.0)b = tf.constant(6.0)c = a * bwith tf.Session():  # We can also use 'c.eval()' here.  print(c.eval())

ABC

错误类 (Error classes)

操作描述class tf.OpError一个基本的错误类型,在当TF执行失败时候报错tf.OpError.op返回执行失败的操作节点,
有的操作如Send或Recv可能不会返回,那就要用用到node_def方法tf.OpError.node_def以NodeDef proto形式表示失败的optf.OpError.error_code描述该错误的整数错误代码tf.OpError.message返回错误信息class tf.errors.CancelledError当操作或者阶段呗取消时候报错class tf.errors.UnknownError未知错误类型class tf.errors.InvalidArgumentError在接收到非法参数时候报错class tf.errors.NotFoundError当发现不存在所请求的一个实体时候,比如文件或目录class tf.errors.AlreadyExistsError当创建的实体已经存在的时候报错class tf.errors.PermissionDeniedError没有执行权限做某操作的时候报错class tf.errors.ResourceExhaustedError资源耗尽时报错class tf.errors.FailedPreconditionError系统没有条件执行某个行为时候报错class tf.errors.AbortedError操作中止时报错,常常发生在并发情形class tf.errors.OutOfRangeError超出范围报错class tf.errors.UnimplementedError某个操作没有执行时报错class tf.errors.InternalError当系统经历了一个内部错误时报出class tf.errors.DataLossError当出现不可恢复的错误
例如在运行 tf.WholeFileReader.read()读取整个文件的同时文件被删减tf.errors.XXXXX.__init__(node_def, op, message)使用该形式方法创建以上各种错误类

----------------------------------------------------------------------------------------------------------------------------------------------------------------------


本文所讲的内容主要为以下列表中相关函数。函数training()通过梯度下降法为最小化损失函数增加了相关的优化操作,在训练过程中,先实例化一个优化函数,比如 tf.train.GradientDescentOptimizer,并基于一定的学习率进行梯度优化训练:

optimizer = tf.train.GradientDescentOptimizer(learning_rate)

然后,可以设置 一个用于记录全局训练步骤的单值。以及使用minimize()操作,该操作不仅可以优化更新训练的模型参数,也可以为全局步骤(global step)计数。与其他tensorflow操作类似,这些训练操作都需要在tf.session会话中进行

global_step = tf.Variable(0, name='global_step', trainable=False)train_op = optimizer.minimize(loss, global_step=global_step)
操作组操作TrainingOptimizers,Gradient Computation,Gradient Clipping,Distributed executionTestingUnit tests,Utilities,Gradient checking

5、Tensorflow函数

5.1 训练 (Training)

一个TFRecords 文件为一个字符串序列。这种格式并非随机获取,它比较适合大规模的数据流,而不太适合需要快速分区或其他非序列获取方式。

优化 (Optimizers)

tf中各种优化类提供了为损失函数计算梯度的方法,其中包含比较经典的优化算法,比如GradientDescent 和Adagrad。

▶▶class tf.train.Optimizer

操作描述class tf.train.Optimizer基本的优化类,该类不常常被直接调用,而较多使用其子类,
比如GradientDescentOptimizer, AdagradOptimizer
或者MomentumOptimizertf.train.Optimizer.__init__(use_locking, name)创建一个新的优化器,
该优化器必须被其子类(subclasses)的构造函数调用tf.train.Optimizer.minimize(loss, global_step=None,
var_list=None, gate_gradients=1,
aggregation_method=None, colocate_gradients_with_ops=False,
name=None, grad_loss=None)
添加操作节点,用于最小化loss,并更新var_list
该函数是简单的合并了compute_gradients()与apply_gradients()函数
返回为一个优化更新后的var_list,如果global_step非None,该操作还会为global_step做自增操作tf.train.Optimizer.compute_gradients(loss,var_list=None, gate_gradients=1,
aggregation_method=None,
colocate_gradients_with_ops=False, grad_loss=None)对var_list中的变量计算loss的梯度
该函数为函数minimize()的第一部分,返回一个以元组(gradient, variable)组成的列表tf.train.Optimizer.apply_gradients(grads_and_vars, global_step=None, name=None)将计算出的梯度应用到变量上,是函数minimize()的第二部分,返回一个应用指定的梯度的操作Operation,对global_step做自增操作tf.train.Optimizer.get_name()获取名称

class tf.train.Optimizer
用法

# Create an optimizer with the desired parameters.opt = GradientDescentOptimizer(learning_rate=0.1)# Add Ops to the graph to minimize a cost by updating a list of variables.# "cost" is a Tensor, and the list of variables contains tf.Variable objects.opt_op = opt.minimize(cost, var_list=<list of variables>)# Execute opt_op to do one step of training:opt_op.run()

▶▶在使用它们之前处理梯度
使用minimize()操作,该操作不仅可以计算出梯度,而且还可以将梯度作用在变量上。如果想在使用它们之前处理梯度,可以按照以下三步骤使用optimizer :

1、使用函数compute_gradients()计算梯度2、按照自己的愿望处理梯度3、使用函数apply_gradients()应用处理过后的梯度

例如:

# 创建一个optimizer.opt = GradientDescentOptimizer(learning_rate=0.1)# 计算<list of variables>相关的梯度grads_and_vars = opt.compute_gradients(loss, <list of variables>)# grads_and_vars为tuples (gradient, variable)组成的列表。#对梯度进行想要的处理,比如cap处理capped_grads_and_vars = [(MyCapper(gv[0]), gv[1]) for gv in grads_and_vars]# 令optimizer运用capped的梯度(gradients)opt.apply_gradients(capped_grads_and_vars)

▶▶选通梯度(Gating Gradients)
函数minimize() 与compute_gradients()都含有一个参数gate_gradient,用于控制在应用这些梯度时并行化的程度。

其值可以取:GATE_NONE, GATE_OP 或 GATE_GRAPH
GATE_NONE : 并行地计算和应用梯度。提供最大化的并行执行,但是会导致有的数据结果没有再现性。比如两个matmul操作的梯度依赖输入值,使用GATE_NONE可能会出现有一个梯度在其他梯度之前便应用到某个输入中,导致出现不可再现的(non-reproducible)结果
GATE_OP: 对于每个操作Op,确保每一个梯度在使用之前都已经计算完成。这种做法防止了那些具有多个输入,并且梯度计算依赖输入情形中,多输入Ops之间的竞争情况出现。
GATE_GRAPH: 确保所有的变量对应的所有梯度在他们任何一个被使用前计算完成。该方式具有最低级别的并行化程度,但是对于想要在应用它们任何一个之前处理完所有的梯度计算时很有帮助的。


Slots

一些optimizer的之类,比如 MomentumOptimizer 和 AdagradOptimizer 分配和管理着额外的用于训练的变量。这些变量称之为’Slots’,Slots有相应的名称,可以向optimizer访问的slots名称。有助于在log debug一个训练算法以及报告slots状态

操作描述tf.train.Optimizer.get_slot_names()返回一个由Optimizer所创建的slots的名称列表tf.train.Optimizer.get_slot(var, name)返回一个name所对应的slot,name是由Optimizer为var所创建
var为用于传入 minimize() 或 apply_gradients()的变量class tf.train.GradientDescentOptimizer使用梯度下降算法的Optimizertf.train.GradientDescentOptimizer.__init__(learning_rate,
use_locking=False, name=’GradientDescent’)构建一个新的梯度下降优化器(Optimizer)class tf.train.AdadeltaOptimizer使用Adadelta算法的Optimizertf.train.AdadeltaOptimizer.__init__(learning_rate=0.001,
rho=0.95, epsilon=1e-08,
use_locking=False, name=’Adadelta’)创建Adadelta优化器class tf.train.AdagradOptimizer使用Adagrad算法的Optimizertf.train.AdagradOptimizer.__init__(learning_rate,
initial_accumulator_value=0.1,
use_locking=False, name=’Adagrad’)创建Adagrad优化器class tf.train.MomentumOptimizer使用Momentum算法的Optimizertf.train.MomentumOptimizer.__init__(learning_rate,
momentum, use_locking=False,
name=’Momentum’, use_nesterov=False)创建momentum优化器
momentum:动量,一个tensor或者浮点值class tf.train.AdamOptimizer使用Adam 算法的Optimizertf.train.AdamOptimizer.__init__(learning_rate=0.001,
beta1=0.9, beta2=0.999, epsilon=1e-08,
use_locking=False, name=’Adam’)创建Adam优化器class tf.train.FtrlOptimizer使用FTRL 算法的Optimizertf.train.FtrlOptimizer.__init__(learning_rate,
learning_rate_power=-0.5,
initial_accumulator_value=0.1,
l1_regularization_strength=0.0,
l2_regularization_strength=0.0,
use_locking=False, name=’Ftrl’)创建FTRL算法优化器class tf.train.RMSPropOptimizer使用RMSProp算法的Optimizertf.train.RMSPropOptimizer.__init__(learning_rate,
decay=0.9, momentum=0.0, epsilon=1e-10,
use_locking=False, name=’RMSProp’)创建RMSProp算法优化器

tf.train.AdamOptimizer
Adam 的基本运行方式,首先初始化:

m_0 <- 0 (Initialize initial 1st moment vector)v_0 <- 0 (Initialize initial 2nd moment vector)t <- 0 (Initialize timestep)

在论文中的 section2 的末尾所描述了更新规则,该规则使用梯度g来更新变量:

t <- t + 1lr_t <- learning_rate * sqrt(1 - beta2^t) / (1 - beta1^t)m_t <- beta1 * m_{t-1} + (1 - beta1) * gv_t <- beta2 * v_{t-1} + (1 - beta2) * g * gvariable <- variable - lr_t * m_t / (sqrt(v_t) + epsilon)

其中epsilon 的默认值1e-8可能对于大多数情况都不是一个合适的值。例如,当在ImageNet上训练一个 Inception network时比较好的选择为1.0或者0.1。
需要注意的是,在稠密数据中即便g为0时, m_t, v_t 以及variable都将会更新。而在稀疏数据中,m_t, v_t 以及variable不被更新且值为零。

梯度计算与截断(Gradient Computation and Clipping)

TensorFlow 提供了计算给定tf计算图的求导函数,并在图的基础上增加节点。优化器(optimizer )类可以自动的计算网络图的导数,但是优化器中的创建器(creators )或者专业的人员可以通过本节所述的函数调用更底层的方法。

操作描述tf.gradients(ys, xs, grad_ys=None, name=’gradients’,
colocate_gradients_with_ops=False, gate_gradients=False,
aggregation_method=None)构建一个符号函数,计算ys关于xs中x的偏导的和,
返回xs中每个x对应的sum(dy/dx)tf.stop_gradient(input, name=None)停止计算梯度,
在EM算法、Boltzmann机等可能会使用到tf.clip_by_value(t, clip_value_min, clip_value_max, name=None)基于定义的min与max对tesor数据进行截断操作,
目的是为了应对梯度爆发或者梯度消失的情况tf.clip_by_norm(t, clip_norm, axes=None, name=None)使用L2范式标准化tensor最大值为clip_norm
返回 t * clip_norm / l2norm(t)tf.clip_by_average_norm(t, clip_norm, name=None)使用平均L2范式规范tensor数据t,
并以clip_norm为最大值
返回 t * clip_norm / l2norm_avg(t)tf.clip_by_global_norm(t_list,
clip_norm, use_norm=None, name=None)返回t_list[i] * clip_norm / max(global_norm, clip_norm)
其中global_norm = sqrt(sum([l2norm(t)**2 for t in t_list]))tf.global_norm(t_list, name=None)返回global_norm = sqrt(sum([l2norm(t)**2 for t in t_list]))


退化学习率(Decaying the learning rate)

操作描述tf.train.exponential_decay(learning_rate, global_step,
decay_steps, decay_rate, staircase=False, name=None)对学习率进行指数衰退

tf.train.exponential_decay

#该函数返回以下结果decayed_learning_rate = learning_rate *         decay_rate ^ (global_step / decay_steps)##例: 以0.96为基数,每100000 步进行一次学习率的衰退global_step = tf.Variable(0, trainable=False)starter_learning_rate = 0.1learning_rate = tf.train.exponential_decay(starter_learning_rate, global_step,                                           100000, 0.96, staircase=True)# Passing global_step to minimize() will increment it at each step.learning_step = (    tf.train.GradientDescentOptimizer(learning_rate)    .minimize(...my loss..., global_step=global_step))


移动平均(Moving Averages)

一些训练优化算法,比如GradientDescent 和Momentum 在优化过程中便可以使用到移动平均方法。使用移动平均常常可以较明显地改善结果。

操作描述class tf.train.ExponentialMovingAverage将指数衰退加入到移动平均中tf.train.ExponentialMovingAverage.apply(var_list=None)对var_list变量保持移动平均tf.train.ExponentialMovingAverage.average_name(var)返回var均值的变量名称tf.train.ExponentialMovingAverage.average(var)返回var均值变量tf.train.ExponentialMovingAverage.variables_to_restore(moving_avg_variables=None)返回用于保存的变量名称的映射

tf.train.ExponentialMovingAverage

# Example usage when creating a training model:# Create variables.var0 = tf.Variable(...)var1 = tf.Variable(...)# ... use the variables to build a training model......# Create an op that applies the optimizer.  This is what we usually# would use as a training op.opt_op = opt.minimize(my_loss, [var0, var1])# Create an ExponentialMovingAverage objectema = tf.train.ExponentialMovingAverage(decay=0.9999)# Create the shadow variables, and add ops to maintain moving averages# of var0 and var1.maintain_averages_op = ema.apply([var0, var1])# Create an op that will update the moving averages after each training# step.  This is what we will use in place of the usual training op.with tf.control_dependencies([opt_op]):    training_op = tf.group(maintain_averages_op)...train the model by running training_op...#Example of restoring the shadow variable values:# Create a Saver that loads variables from their saved shadow values.shadow_var0_name = ema.average_name(var0)shadow_var1_name = ema.average_name(var1)saver = tf.train.Saver({shadow_var0_name: var0, shadow_var1_name: var1})saver.restore(...checkpoint filename...)# var0 and var1 now hold the moving average values

tf.train.ExponentialMovingAverage.variables_to_restore

  variables_to_restore = ema.variables_to_restore()  saver = tf.train.Saver(variables_to_restore)


协调器和队列运行器(Coordinator and QueueRunner)

查看queue中,queue相关的内容,了解tensorflow中队列的运行方式。

操作描述class tf.train.Coordinator线程的协调器tf.train.Coordinator.clear_stop()清除停止标记tf.train.Coordinator.join(threads=None, stop_grace_period_secs=120)等待线程终止
threads:一个threading.Threads的列表,启动的线程,将额外加入到registered的线程中tf.train.Coordinator.register_thread(thread)Register一个用于join的线程tf.train.Coordinator.request_stop(ex=None)请求线程结束tf.train.Coordinator.should_stop()检查是否被请求停止tf.train.Coordinator.stop_on_exception()上下文管理器,当一个例外出现时请求停止tf.train.Coordinator.wait_for_stop(timeout=None)等待Coordinator提示停止进程class tf.train.QueueRunner持有一个队列的入列操作列表,用于线程中运行
queue:一个队列
enqueue_ops: 用于线程中运行的入列操作列表tf.train.QueueRunner.create_threads(sess,
coord=None, daemon=False, start=False)创建运行入列操作的线程,返回一个线程列表tf.train.QueueRunner.from_proto(queue_runner_def)返回由queue_runner_def创建的QueueRunner对象tf.train.add_queue_runner(qr, collection=’queue_runners’)增加一个QueueRunner到graph的收集器(collection )中tf.train.start_queue_runners(sess=None, coord=None, daemon=True, start=True, collection=’queue_runners’)启动所有graph收集到的队列运行器(queue runners)

class tf.train.Coordinator

#Coordinator的使用,用于多线程的协调try:  ...  coord = Coordinator()  # Start a number of threads, passing the coordinator to each of them.  ...start thread 1...(coord, ...)  ...start thread N...(coord, ...)  # Wait for all the threads to terminate, give them 10s grace period  coord.join(threads, stop_grace_period_secs=10)except RuntimeException:  ...one of the threads took more than 10s to stop after request_stop()  ...was called.except Exception:  ...exception that was passed to coord.request_stop()

tf.train.Coordinator.stop_on_exception()

with coord.stop_on_exception():  # Any exception raised in the body of the with  # clause is reported to the coordinator before terminating  # the execution of the body.  ...body...#等价于try:  ...body...exception Exception as ex:  coord.request_stop(ex)


布执行(Distributed execution)

可以阅读TensorFlow的分布式学习框架简介查看更多tensorflow分布式细节。

操作描述class tf.train.Server一个进程内的tensorflow服务,用于分布式训练tf.train.Server.init(server_or_cluster_def,
job_name=None, task_index=None, protocol=None,
config=None, start=True)创建一个新的服务,其中job_name, task_index,
和protocol为可选参数,
优先级高于server_or_cluster_def中相关信息
server_or_cluster_def : 为一个tf.train.ServerDef
或 tf.train.ClusterDef 协议(protocol)的buffer,
或者一个tf.train.ClusterSpec对象tf.train.Server.create_local_server(config=None, start=True)创建一个新的运行在本地主机的单进程集群tf.train.Server.target返回tf.Session所连接的目标服务器tf.train.Server.server_def返回该服务的tf.train.ServerDeftf.train.Server.start()开启服务tf.train.Server.join()阻塞直到服务已经关闭# class tf.train.Supervisor一个训练辅助器,用于checkpoints模型以及计算的summaries。该监视器只是一个小的外壳(wrapper),用于Coordinator, a Saver, 和a SessionManager周围tf.train.Supervisor.__init__(graph=None, ready_op=0, is_chief=True, init_op=0, init_feed_dict=None, local_init_op=0, logdir=None,
summary_op=0, saver=0, global_step=0,
save_summaries_secs=120, save_model_secs=600,
recovery_wait_secs=30, stop_grace_secs=120,
checkpoint_basename=’model.ckpt’, session_manager=None, summary_writer=0, init_fn=None)
创建一个监视器Supervisortf.train.Supervisor.managed_session(master=”, config=None, start_standard_services=True, close_summary_writer=True)返回一个管路session的上下文管理器tf.train.Supervisor.prepare_or_wait_for_session(master=”, config=None, wait_for_checkpoint=False, max_wait_secs=7200, start_standard_services=True)确保model已经准备好tf.train.Supervisor.start_standard_services(sess)为sess启动一个标准的服务tf.train.Supervisor.start_queue_runners(sess, queue_runners=None)为QueueRunners启动一个线程,queue_runners为一个QueueRunners列表tf.train.Supervisor.summary_computed(sess, summary, global_step=None)指示计算的summarytf.train.Supervisor.stop(threads=None, close_summary_writer=True)停止服务以及协调器(coordinator),并没有关闭sessiontf.train.Supervisor.request_stop(ex=None)参考Coordinator.request_stop()tf.train.Supervisor.should_stop()参考Coordinator.should_stop()tf.train.Supervisor.stop_on_exception()参考 Coordinator.stop_on_exception()tf.train.Supervisor.Loop(timer_interval_secs, target, args=None, kwargs=None)开启一个循环器线程用于调用一个函数
每经过timer_interval_secs秒执行,target(*args, **kwargs)tf.train.Supervisor.coord返回监督器(Supervisor)使用的协调器(Coordinator )# class tf.train.SessionManager训练的辅助器,用于从checkpoint恢复数据以及创建一个sessiontf.train.SessionManager.__init__(local_init_op=None, ready_op=None, graph=None, recovery_wait_secs=30)创建一个SessionManagertf.train.SessionManager.prepare_session(master, init_op=None, saver=None, checkpoint_dir=None, wait_for_checkpoint=False, max_wait_secs=7200, config=None, init_feed_dict=None, init_fn=None)创建一个session,并确保model可以被使用tf.train.SessionManager.recover_session(master, saver=None, checkpoint_dir=None, wait_for_checkpoint=False, max_wait_secs=7200, config=None)创建一个session,如果可以的话,使用恢复方法创建tf.train.SessionManager.wait_for_session(master, config=None, max_wait_secs=inf)创建一个session,并等待model准备完成# class tf.train.ClusterSpec将一个集群表示为一系列“tasks”,并整合至“jobs”中tf.train.ClusterSpec.as_cluster_def()返回该cluster中一个tf.train.ClusterDef协议的buffertf.train.ClusterSpec.as_dict()返回一个字典,由job名称对应于网络地址tf.train.ClusterSpec.job_tasks(job_name)返回一个给定的job对应的task列表tf.train.ClusterSpec.jobs返回该cluster的job名称列表tf.train.replica_device_setter(ps_tasks=0, ps_device=’/job:ps’, worker_device=’/job:worker’, merge_devices=True, cluster=None, ps_ops=None)返回一个设备函数(device function),以在建立一个副本graph的时候使用,设备函数(device function)用在with tf.device(device_function)中

tf.train.Server

server = tf.train.Server(...)with tf.Session(server.target):  # ...

tf.train.Supervisor
相关参数:
ready_op : 一维 字符串 tensor。该tensor是用过监视器在prepare_or_wait_for_session()计算,检查model是否准备好可以使用。如果准备好,将返回一个空阵列,如果为None,该model没有被检查。
is_chief : 如果为True,创建一个主监视器用于负责初始化与模型的恢复,若为False,则依赖主监视器。
init_op : 一个操作,用于模型不能恢复时的初始化操作。默认初始化所有操作
local_init_op : 可被所有监视器运行的初始化操作。
logdir : 设置log目录
summary_op : 一个操作(Operation ),返回Summary 和事件logs,需要设置 logdir
saver : 一个Saver对象
save_summaries_secs : 保存summaries的间隔秒数
save_model_secs : 保存model的间隔秒数
checkpoint_basename : checkpoint保存的基本名称

  • 使用在单进程中
with tf.Graph().as_default():  ...add operations to the graph...  # Create a Supervisor that will checkpoint the model in '/tmp/mydir'.  sv = Supervisor(logdir='/tmp/mydir')  # Get a TensorFlow session managed by the supervisor.  with sv.managed_session(FLAGS.master) as sess:    # Use the session to train the graph.    while not sv.should_stop():      sess.run(<my_train_op>)# 在上下文管理器with sv.managed_session()内,所有在graph的变量都被初始化。# 或者说,一些服务器checkpoint相应模型并增加summaries至事件log中。# 如果有例外发生,should_stop()将返回True
  • 使用在多副本运行情况中
    要使用副本训练已经部署在集群上的相同程序,必须指定其中一个task为主要,该task处理 initialization, checkpoints, summaries, 和recovery相关事物。其他task依赖该task。
# Choose a task as the chief. This could be based on server_def.task_index,# or job_def.name, or job_def.tasks. It's entirely up to the end user.# But there can be only one *chief*.is_chief = (server_def.task_index == 0)server = tf.train.Server(server_def)with tf.Graph().as_default():  ...add operations to the graph...  # Create a Supervisor that uses log directory on a shared file system.  # Indicate if you are the 'chief'  sv = Supervisor(logdir='/shared_directory/...', is_chief=is_chief)  # Get a Session in a TensorFlow server on the cluster.  with sv.managed_session(server.target) as sess:    # Use the session to train the graph.    while not sv.should_stop():      sess.run(<my_train_op>)

如果有task崩溃或重启,managed_session() 将检查是否Model被初始化。如果已经初始化,它只需要创建一个session并将其返回至正在训练的正常代码中。如果model需要被初始化,主task将对它进行重新初始化,而其他task将等待模型初始化完成。
注意:该程序方法一样适用于单进程的work,该单进程标注自己为主要的便行

supervisor中master的字符串形式
无论运行在本机或者集群上,都可以使用以下值设定master flag:

  • 定义为 ” ,要求一个进程内且没有使用RPC的session
  • 定义为 ‘local’,要求一个使用基于RPC的主服务接口(“Master interface” )的session来运行tensorflow程序。更多细节可以查看 tf.train.Server.create_local_server()相关内容。
  • 定义为 ‘grpc://hostname:port’,要求一个指定的RPC接口的session,同时运行内部进程的master接入远程的tensorflow workers。可用server.target返回该形式

supervisor高级用法

  • 启动额外的服务
    managed_session()启动了 Checkpoint 和Summary服务。如果需要运行更多的服务,可以在managed_session()控制的模块中启动他们。
#例如: 开启一个线程用于打印loss. 设置每60秒该线程运行一次,我们使用sv.loop() ...  sv = Supervisor(logdir='/tmp/mydir')  with sv.managed_session(FLAGS.master) as sess:    sv.loop(60, print_loss, (sess))    while not sv.should_stop():      sess.run(my_train_op)
  • 启动更少的的服务
    managed_session() 启动了 “summary” 和 “checkpoint” 线程,这些线程通过构建器或者监督器默认自动创建了summary_op 和saver操作。如果想运行自己的 summary 和checkpointing方法,关闭这些服务,通过传递None值给summary_op 和saver参数。
在chief中每100个step,创建summaries  # Create a Supervisor with no automatic summaries.  sv = Supervisor(logdir='/tmp/mydir', is_chief=is_chief, summary_op=None)  # As summary_op was None, managed_session() does not start the  # summary thread.  with sv.managed_session(FLAGS.master) as sess:    for step in xrange(1000000):      if sv.should_stop():        break      if is_chief and step % 100 == 0:        # Create the summary every 100 chief steps.        sv.summary_computed(sess, sess.run(my_summary_op))      else:        # Train normally        sess.run(my_train_op)

tf.train.Supervisor.managed_session

def train():  sv = tf.train.Supervisor(...)  with sv.managed_session(<master>) as sess:    for step in xrange(..):      if sv.should_stop():        break      sess.run(<my training op>)      ...do other things needed at each training step...
  • 1

tf.train.SessionManager

with tf.Graph().as_default():   ...add operations to the graph...  # Create a SessionManager that will checkpoint the model in '/tmp/mydir'.  sm = SessionManager()  sess = sm.prepare_session(master, init_op, saver, checkpoint_dir)  # Use the session to train the graph.  while True:    sess.run(<my_train_op>)#其中prepare_session()初始化和恢复一个模型参数。 #另一个进程将等待model准备完成,代码如下with tf.Graph().as_default():  ...add operations to the graph...  # Create a SessionManager that will wait for the model to become ready.  sm = SessionManager()  sess = sm.wait_for_session(master)  # Use the session to train the graph.  while True:    sess.run(<my_train_op>)#wait_for_session()等待一个model被其他进程初始化

tf.train.ClusterSpec
一个tf.train.ClusterSpec表示一系列的进程,这些进程都参与分布式tensorflow的计算。每一个 tf.train.Server都在一个独有的集群中构建。
创建一个具有两个jobs及其5个tasks的集群们需要定义从job名称列表到网络地址列表之间的映射。

cluster = tf.train.ClusterSpec({"worker": ["worker0.example.com:2222",                                           "worker1.example.com:2222",                                           "worker2.example.com:2222"],                                "ps": ["ps0.example.com:2222",                                       "ps1.example.com:2222"]})
  • 1

tf.train.replica_device_setter

# To build a cluster with two ps jobs on hosts ps0 and ps1, and 3 worker# jobs on hosts worker0, worker1 and worker2.cluster_spec = {    "ps": ["ps0:2222", "ps1:2222"],    "worker": ["worker0:2222", "worker1:2222", "worker2:2222"]}with tf.device(tf.replica_device_setter(cluster=cluster_spec)):  # Build your graph  v1 = tf.Variable(...)  # assigned to /job:ps/task:0  v2 = tf.Variable(...)  # assigned to /job:ps/task:1  v3 = tf.Variable(...)  # assigned to /job:ps/task:0# Run compute


汇总操作(Summary Operations)

我们可以在一个session中获取summary操作的输出,并将其传输到SummaryWriter以添加至一个事件记录文件中。

操作描述tf.scalar_summary(tags, values, collections=None, name=None)输出一个标量值的summary协议buffer
tag的shape需要与values的相同,用来做summaries的tags,为字符串tf.image_summary(tag, tensor, max_images=3, collections=None, name=None)输出一个图像tensor的summary协议buffertf.audio_summary(tag, tensor, sample_rate, max_outputs=3, collections=None, name=None)输出一个音频tensor的summary协议buffertf.histogram_summary(tag, values, collections=None, name=None)输出一个直方图的summary协议buffertf.nn.zero_fraction(value, name=None)返回0在value中的小数比例tf.merge_summary(inputs, collections=None, name=None)合并summarytf.merge_all_summaries(key=’summaries’)合并在默认graph中手机的summaries

▶▶将记录汇总写入文件中(Adding Summaries to Event Files)

操作描述class tf.train.SummaryWriter将summary协议buffer写入事件文件中tf.train.SummaryWriter.__init__(logdir, graph=None, max_queue=10, flush_secs=120, graph_def=None)创建一个SummaryWriter实例以及新建一个事件文件tf.train.SummaryWriter.add_summary(summary, global_step=None)将一个summary添加到事件文件中tf.train.SummaryWriter.add_session_log(session_log, global_step=None)添加SessionLog到一个事件文件中tf.train.SummaryWriter.add_event(event)添加一个事件到事件文件中tf.train.SummaryWriter.add_graph(graph, global_step=None, graph_def=None)添加一个Graph到时间文件中tf.train.SummaryWriter.add_run_metadata(run_metadata, tag, global_step=None)为一个单一的session.run()调用添加一个元数据信息tf.train.SummaryWriter.flush()刷新时间文件到硬盘中tf.train.SummaryWriter.close()将事件问价写入硬盘中并关闭该文件tf.train.summary_iterator(path)一个用于从时间文件中读取时间协议buffer的迭代器

tf.train.SummaryWriter
创建一个SummaryWriter 和事件文件。如果我们传递一个Graph进入该构建器中,它将被添加到事件文件当中,这一点与使用add_graph()具有相同功能。
TensorBoard 将从事件文件中提取该graph,并将其显示。所以我们能直观地看到我们建立的graph。我们通常从我们启动的session中传递graph:

...create a graph...# Launch the graph in a session.sess = tf.Session()# Create a summary writer, add the 'graph' to the event file.writer = tf.train.SummaryWriter(<some-directory>, sess.graph)

tf.train.summary_iterator

#打印时间文件中的内容for e in tf.train.summary_iterator(path to events file):    print(e)#打印指定的summary值# This example supposes that the events file contains summaries with a# summary value tag 'loss'.  These could have been added by calling# `add_summary()`, passing the output of a scalar summary op created with# with: `tf.scalar_summary(['loss'], loss_tensor)`.for e in tf.train.summary_iterator(path to events file):    for v in e.summary.value:        if v.tag == 'loss':            print(v.simple_value)
  • 1


训练的通用函数及其他(Training utilities)

操作描述tf.train.global_step(sess, global_step_tensor)一个用于获取全局step的小辅助器tf.train.write_graph(graph_def, logdir, name, as_text=True)将一个graph proto写入一个文件中#  :—class tf.train.LooperThread可重复地执行代码的线程tf.train.LooperThread.init(coord, timer_interval_secs, target=None, args=None, kwargs=None)创建一个LooperThreadtf.train.LooperThread.is_alive()返回是否该线程是活跃的tf.train.LooperThread.join(timeout=None)等待线程结束tf.train.LooperThread.loop(coord, timer_interval_secs, target, args=None, kwargs=None)启动一个LooperThread,用于周期地调用某个函数
调用函数target(args)tf.py_func(func, inp, Tout, stateful=True, name=None)将python函数包装成tf中操作节点

tf.train.global_step

# Creates a variable to hold the global_step.global_step_tensor = tf.Variable(10, trainable=False, name='global_step')# Creates a session.sess = tf.Session()# Initializes the variable.sess.run(global_step_tensor.initializer)print('global_step: %s' % tf.train.global_step(sess, global_step_tensor))global_step: 10

tf.train.write_graph

v = tf.Variable(0, name='my_variable')sess = tf.Session()tf.train.write_graph(sess.graph_def, '/tmp/my-model', 'train.pbtxt')

tf.py_func

#tf.py_func(func, inp, Tout, stateful=True, name=None)#func:为一个python函数#inp:为输入函数的参数,Tensor列表#Tout: 指定func返回的输出的数据类型,是一个列表def my_func(x):  # x will be a numpy array with the contents of the placeholder below  return np.sinh(x)inp = tf.placeholder(tf.float32, [...])y = py_func(my_func, [inp], [tf.float32])

5.2 测试 (Testing)

TensorFlow 提供了一个方便的继承unittest.TestCase类的方法,该类增加有关TensorFlow 测试的方法。如下例子:

import tensorflow as tfclass SquareTest(tf.test.TestCase):  def testSquare(self):    with self.test_session():      x = tf.square([2, 3])      self.assertAllEqual(x.eval(), [4, 9])if __name__ == '__main__':  tf.test.main()


共用(Utilities)

操作描述tf.test.main()运行所有的单元测试tf.test.assert_equal_graph_def(actual, expected)断言 两个GraphDefs 是否几乎一样tf.test.get_temp_dir()返回测试期间使用的临时目录tf.test.is_built_with_cuda()返回是否Tensorflow支持CUDA(GPU)的build


梯度检查(Gradient checking)

可对比compute_gradient 和compute_gradient_error函数的用法

操作描述tf.test.compute_gradient(x, x_shape, y, y_shape, x_init_value=None, delta=0.001, init_targets=None)计算并返回理论的和数值的Jacobian矩阵tf.test.compute_gradient_error(x, x_shape, y, y_shape, x_init_value=None, delta=0.001, init_targets=None)计算梯度的error。在计算所得的与数值估计的Jacobian中 为dy/dx计算最大的error


--------------------------------------------------------------------------------------------------------------------

参考文献

Tensorflow一些常用基本概念与函数 http://www.cnblogs.com/wuzhitj/archive/2017/03.html

Tensorflow笔记:常用函数说明: http://blog.csdn.net/u014595019/article/details/52805444

Tensorflow一些常用基本概念与函数(1) http://blog.csdn.net/lenbow/article/details/52152766
Tensorflow一些常用基本概念与函数(2) http://blog.csdn.net/lenbow/article/details/52181159
Tensorflow一些常用基本概念与函数(3) http://blog.csdn.net/lenbow/article/details/52213105

Tensorflow一些常用基本概念与函数(4)http://blog.csdn.net/lenbow/article/details/52218551


原创粉丝点击