Tensorflow 主要依赖包 Protocol buffer, bazel 此处偷乐3秒钟,哈哈哈哈
Bazel 支持的编译方式有 py_binary, py_library, py_test
挖坑:docker使用
tensor 张量 阶数和括号的数量一样,
一阶: []
二阶:[[],[]]
类型需要注意
1 2 3 4 5 import tensorflow as tfa = tf.constant([1 , 2 ], name="a" ) b = tf.constant([2.0 , 3.0 ], name="b" ) result = tf.add(a, b, name="add" ) print (result)
全联接层 2层之间任意2个节点都有边
$W$ 表示的是边,
snippet 1 2 3 4 5 config = tf.ConfigProto() config.gpu_options.allow_growth=True with tf.Session(config=config) as sess: print (sess.run(result)) print (result.eval (session=sess))
激活函数,非线性 ReLU $f(x) = max(x, 0)$
sigmod $f(x) = \frac{1}{1 + e^{-x}}$
tanh $f(x) = \frac{1 - e^{-2x}}{1 + e^{-2x}}$
softmax 在分类问题中用来归一化最后输出的概率,使得它们的和为1
$softmax(y) = \frac{e^{yi}}{\sum_{j=1}^{n}e^{yi}}$
开始的输出的是每个类的概率,经过这个转换后变成了一个概率分布,强。
交叉熵 用来衡量2个概率分布的差异
$H(p,q) = -\sum_{x}p(x)log q(x)$
按照字面意思,如果交叉熵越大,那么2个概率分布应该会越大,那就错了!🍎🍎 吓得我吃了2个苹果
其实交叉熵的含义是指求熵的时候的交叉
反而,交叉熵越小,2个概率分布差距越小
tf.clip_by_value tf.clip_by_value(v, low, upp)
1 2 3 4 5 6 7 8 v = tf.constant([[1.0 , 2.0 , 3.0 ], [4.0 , 5.0 , 6.0 ]]) config = tf.ConfigProto() config.gpu_options.allow_growth=True with tf.Session(config=config) as sess: print (tf.clip_by_value(v, 2.5 , 4.5 ).eval (session=sess)) [[ 2.5 2.5 3. ] [ 4. 4.5 4.5 ]]
* 和 matmul的区别 1 2 3 4 5 6 7 v1 = tf.constant([[1.0 , 2.0 ], [3.0 , 4.0 ]]) v2 = tf.constant([[5.0 , 6.0 ], [7.0 , 8.0 ]]) config = tf.ConfigProto() config.gpu_options.allow_growth=True with tf.Session(config=config) as sess: print ((v1 * v2).eval (sessi fon=sess)) print (tf.matmul(v1, v2).eval (session=sess))
reduce_mean 0是列,1是行
1 2 3 4 x = tf.constant([[1. , 1. ], [2. , 2. ]]) tf.reduce_mean(x) tf.reduce_mean(x, 0 ) tf.reduce_mean(x, 1 )
random 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 from numpy.random import RandomStatedataset_size = 10 X = rdm.rand(dataset_size, 2 ) print (X)[[ 0.5747115 0.6280762 ] [ 0.28557628 0.58683334 ] [ 0.75002176 0.85831384 ] [ 0.75508219 0.69805725 ] [ 0.86447943 0.322681 ] [ 0.67078879 0.45087394 ] [ 0.38210275 0.41081135 ] [ 0.40147958 0.31738395 ] [ 0.62191937 0.43024727 ] [ 0.97380208 0.67780089 ]]
stochastic gradient descent 每次选一条数据进行计算损失函数
因为举个🌰, y=wx, 那么其实w的梯度是和x相关的。
batch 的方法 取个折中,使用部分的数据进行计算梯度
学习率的衰减 目的是使得前期的时候快速接近较优解,后期的时候不要有太大的波动。
1 2 decayed_learning_rate = \ learning_reate * decay_rate ^ (global_step / decay_steps)
其中decay_steps是所有数据数量总和/batch_size。所以用完一遍数据就*decay_rate一次
Global_step是当前的迭代次数。
tf参数staircase的含义
1 2 3 4 5 6 7 8 global_step = tf.Variable(0 ) learning_rate = tf.train.exponential_decay(0.1 , global_step, 100 , 0.96 , staircase=False ) learning_step = tf.train.GradientDescentOptimizer(learning_rate)\ .minimize(...my loss..., global_step=global_step)
正则化 L1 $R(w) = \sum_{i}|w_i|$
L2 $R(w) = \sum_{i}|w_i^2|$
理解 L1更佳容易使得参数等于0,因为在L2中如果一个数字为0.001平方后就很小了被忽略了。
计算技巧 交叉熵 y_ 是真实值
1 2 cross_entropy = -tf.reduce_mean( y_ * tf.log(tf.clip_by_value(y, 1e-10 , 1.0 )))
真正的算法应该是对于矩阵 [[1.0, 2.0, 3.0], [4.0, 5.0, 6.0]],先每行求和然后再取平均。现在是直接对所有的数字取了平均,这样不会改变结果因为差的是一个D系数。
总之在多分类问题中,
Ground truth是一堆概率值表示了这个东西属于某个类的概率
但是算法输出的也是一堆值,表示这个东西属于某个类的概率,但是不保证输出的概率和是1,所以通过exp{x}然后归一化后,使得概率的和为1,然后再通过交叉熵比较2个概率分布的差异。交叉熵越小的越好
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 import tensorflow as tfdef get_weight (shape, lambda ): var = tf.Variable(tf.random_normal(shape), dtype=tf.float32) tf.add_to_collection('losses' , tf.contrib.layers.l2_regularizer(lambda )(var)) return var x = tf.placeholder(tf.float32, shape=(None ,2 )) y_= tf.placeholder(tf.float32, shape=(None ,1 )) batch_size = 8 layer_dimension = [2 , 10 , 10 , 10 , 1 ] n_layers = len (layer_dimension) cur_layer = x in_dimension = layer_dimension[0 ] for i in range (1 , n_layers): out_dimension = layer_dimension[i] weight = get_weight([in_dimension, out_dimension], 0.0001 ) bias = tf.Variable(tf.constant(0.1 , shape=[out_dimension])) cur_layer = tf.nn.relu(tf.matmul(cur_layer, weight) + bias) in_dimension = layer_dimension[i] mse_loss = tf.reduce_mean(tf.square(y_ - cur_layer)) tf.add_to_collection('losses' , mse_loss) loss = tf.add_n(tf.get_collection('losses' ))
MNIST数字识别 6w张训练数据,1w张测试数据
图片大小是28*28,数字出现在正中间
白色背景 background
黑色前景 foreground
tf.cast(x, tf.float32) 类型强制转换
结论 调整网络结构对最后的影响很大
滑动平均模型和指数衰减都是限制神经网络中参数更新的速度,
正则化的作用更加大
变量管理 1 2 v = tf.get_variable("v" , shape=[1 ], initializer=tf.constant_initializer(1.0 )) v = tf.Variable(tf.constant(1.0 , shape=[1 ], name="v" ))
升级api变化 tf.select->tf.where
疑问 1 2 3 4 5 w = tf.Variable(tf.random_normal([2 ,1 ], stddev=1 , seed=1 )) y = tf.matmul(x, w) loss = tf.reduce_mean(tf.square(y_ - y)) \ + tf.contrib.layers.l2_regularizer(lambda )(w)