Python_ML-Day04: 深度学习、Tensorflow 1.Tensorflow特点 - 真正的可移植性 引入各种计算设备的支持包括CPU/GPU/TPU,以及能够很好地运行在移动端, 如安卓设备、ios、树莓派等等 - 多语言支持 Tensorflow 有一个合理的c++使用界面,也有一个易用的python使用界面来构建和 执行你的graphs,你可以直接写python/c++程序。 - 高度的灵活性与效率 TensorFlow是一个采用数据流图(data flow graphs),用于数值计算的开源软件库 能够灵活进行组装图,执行图。随着开发的进展,Tensorflow的效率不算在提高 - 支持TensorFlow 由谷歌提供支持,谷歌投入了大量精力开发 TensorFlow,它希望 TensorFlow 成为机器学习研究人员和开发人员的通用语言 2.安装 pip3 install tensorflow pip3 install tensorflow==1.14 3.数据流图 - Tensor: 张量,数据 - operation: op算子,专门运算的操作节点.所有操作都是一个op - graph: 图, 这个程序的结构 - 由Tensor 和 op 组成的图 - session: 会话, 运算图 4.图 Graph: 图包含了一组op, tensor 和 一个会话session - 创建图:tf.Graph() - 使用图: # 创建一张图 g = tf.Graph() # 使用图 with g.as_default(): a = tf.constant(5.0) b = tf.constant(6.0) sum1 = tf.add(a, b) with tf.Session() as sess: print(sess.run(sum1)) 5.op 与 tensor 的区别 op: 只要使用tensorflow 的 api 定义的函数或者类,都是op. 即 tf. 点出来的都是算子 tensor: 张量 指代的数据。仅仅是数据。 可以是 op 里面的数据。即 op 里面是可以有tensor的。算子可以包括运算和数据 6.会话Session - 运行TensorFlow操作图的类,使用默认注册的图,也可以指定 - tf.Session() - 会话资源 会话可能拥有很多资源,如 tf.Variable,tf.QueueBase 和tf.ReaderBase,会话结束后需要进行资源释放 - sess = tf.Session() sess.run(...) sess.close() - 使用上下文管理器,自动关闭session with tf.Session() as sess: sess.run(...) - 可以给会话添加配置项: 比如打印log: config=tf.ConfigProto(log_device_placement=True) - 交互式:tf.InteractiveSession() - 命令行使用 - 会话的run(fetches, feed_dict=None,graph=None): 0. fetches: 要运行的ops 1. 不是op 不能运行 2. 但有重载机制: + - * / 可以重载 比如: run(2 + 3)错 run(op + 2)可以 3. placeholder 可以实时的提供训练的数据 - placeholder(占位符) + feed_dict - plt = tf.placeholder(tf.float32, [2,3]) -- 表示一个类型是float32的2行3列的数据占位,但是没有实际的数据 - plt = tf.placeholder(tf.float32, [None,3]) -- 表示一个类型是float32的 不定行 3列 的数据占位,但是没有实际的数据 - sess.run(plt, feed_dict={plt:[[1,2,3],[3,4,5]]}) - feed_dict: 是一个字典 允许调用者覆盖图中指定张量的值,提供给placeholder使用 4. 返回值异常 RuntimeError:如果它Session处于无效状态(例如已关闭)。 TypeError:如果fetches或feed_dict键是不合适的类型。 ValueError:如果fetches或feed_dict键无效或引用 Tensor不存在。 7.张量 - tensorflow基本的数据类型 - 一个类型化的N纬度数组 tf.tensor - 三部分组成: 数据类型,形状[非常重要],名字 - 形状: 0阶/1阶/2阶/n阶 - 类型: tf.float32/float64/int32/int64/uint8/ - 属性: 1. graph 张量所在的图 2. op 张量的操作名 3. name 张量的字符串描述 4. shape 张量形状 - 0维 = () - 1维 = (?) - 2维 = (?,?) - 动态形状和静态形状: 在张量的变化中,有没有生成一个新的张量数据 1.静态形状 - 创建一个张量之后,默认的形状。初始状态的形状 - tf.Tensor.get_shape 获取静态形状 - tf.Tensor.set_shape 更新对象的静态形状。通常用于在不能直接推断的情况下 2.动态形状 - 一种动态变化,一种描述原始张量在执行过程中的一种形状 - tf.reshape: 创建一个具有不同动态形状的新张量 3.注意 - 转换静态形状的时候,1D-1D,2D-2D,但是不能跨阶 2D-3D - 对于已经固定或者set静态形状的张量,不能再次设置静态形状 - tf.reshape 创建动态形状,元素个数要保持一致 8.张量的操作 - 创建固定值张量 tf.zeros() tf.ones() tf.constant() - 创建随机张量 1. 通过正态分布去创建[正态分布-平均值和标准差] tf.random_normal() - 代码 # 全是0 的张量 zero = tf.zeros(shape=[3, 4], dtype=tf.float32) # 全是1 的张量 print(zero.eval()) zero = tf.ones(shape=[3, 4], dtype=tf.float32) print(zero.eval()) # 指定张量 cons = tf.constant(value=[5, 1], shape=[3, 3], dtype=tf.float32) print(cons.eval()) # 创建随机张量 random = tf.random_normal(shape=[3, 3], mean=6, stddev=1.0, dtype=tf.float32) print(random.eval()) - 改变张量类型 tf.string_to_number(string_tensor, out_type, name) tf.cast(tensor, dtype, name) - 切片与拓展 tf.concat() 9.变量 - 变量也是一种op. 是一种特殊的张量。能够进行持久化存储。它的值就是张量,默认被训练 - 创建一个带值initial_value的新变量: tf.Variable(initial_value=None,name=None) 0.initial_value:需要持久化的张量或者op 1.assign(value):为变量分配一个新值,返回新值 2.eval(session=None):计算并返回此变量的值 3.name属性表示变量名字 - 定义一个变量op的时候,一定要在会话当中运行初始化 def variable(): """ 变量 :return: """ # 初始化一个变量 random = tf.random_normal([2, 3], mean=0, stddev=1.0) v1 = tf.Variable(random) print(v1) # 变量不能直接计算,必须先做显示的初始化操作 init_op = tf.global_variables_initializer() with tf.Session() as sess: sess.run(init_op) print(sess.run(v1)) 10. 可视化学习Tensorboard - 步骤 1. 将你的程序图结构序列化成事件文件events 2. 使用Tensorboard,读取事件文件,显示图形 - summary: 摘要 1. tf.summary.FileWriter('/tmp/tensorflow/summary/test/', graph=default_graph) - 返回filewriter,写入事件文件到指定目录(最好用绝对路径),以提供给tensorboard使用 - graph = sess.graph 2.开启 - tensorboard --logdir="/tmp/tensorflow/summary/test/" - 一般浏览器打开为127.0.0.1:6006 - 注:修改程序后,再保存一遍会有新的事件文件,打开默认为最新 11.自定义一个线性回归案例 - 步骤分析 1. 准备好数据 - 比如 1个特征值和1个目标值,总计100个样本 2. 建立模型 - 随机初始化准备一组权重w, 一个偏置 b - y = wx + b - 模型的参数,必须用变量初始化。因为要迭代 3. 求损失函数,均方误差 - (y1-y1`)^2 + (y2-y2`)^2 + ... + (y1-y100`)^2 / 100 4. 指定学习率,使用梯度下降去求解最优解 - 工具分析 1. 矩阵相乘 tf.matmul(x,w) [m,n] * [n,1] = [m,1] 2. 平方 tf.square(error) 3. 均值 tf.reduce_mean(error) 4. 梯度下降优化器 - tf.train.GradientDescentOptimizer(learning_rate) - learning_rate:学习率 - return:梯度下降op - 梯度爆炸/梯度消失 1. 在极端的情况下,权重的值变得非常大,以至于溢出,导致Nan 2. 如何解决梯度爆炸? - 重新设计网络 - 调整学习率 - 使用梯度截断: 在训练过程中检查和限制梯度的大小 - 使用激活函数 12.作用域 - with tf.variable_scope("a"): - 作用 1. 让模型代码更加清晰,作用分明 13.增加变量显示 - 观察模型的参数、损失值等变量的变化 - 步骤 1. 收集变量:添加权重参数,损失值等需要检测变化的变量,到tensorboard - tf.summary.scalar(name=’’,tensor) 收集对于损失函数和准确率 等单值变量,name为变量的名字,tensor为值 - tf.summary.histogram(name=‘’,tensor) 收集高维度的变量参数 - tf.summary.image(name=‘’,tensor) 收集输入的图片张量能显示图片 2. 合并变量并写入事件文件 - merged = tf.summary.merge_all() - 运行合并:summary = sess.run(merged),每次迭代都需运行 - 添加:FileWriter.add_summary(summary,i),i表示第几次的值 14.模型的保存与加载 - tf.train.Saver(var_list=None,max_to_keep=5) 1. var_list:指定将要保存和还原的变量。它可以作为一个dict或一个列表传递. 2. max_to_keep:指示要保留的最近检查点文件的最大数量。 创建新文件时,会删除较旧的文件。如果无或0,则保留所有 检查点文件。默认为5(即保留最新的5个检查点文件。) - 保存:saver.save(sess, '/tmp/ckpt/test/model') - 加载:saver.restore(sess, '/tmp/ckpt/test/model') - 保存文件格式:checkpoint文件 15.自定义命令行参数 - 步骤 1. 首先定义有哪些参数需要在运行时指定 - tf.app.flags.DEFINE_integer("flagname","default_value,"DESC") - tf.app.flags.DEFINE_integer("max_step",100,"模型训练的步数") 2. 程序当中获取传入的参数 - FLAGS = tf.app.flags.FLAGS - FLAGS.max_step 16.源码 import tensorflow as tf import os os.environ['TF_CPP_MIN_LOG_LEVEL'] = '2' # # 创建一张图 # g = tf.Graph() # # 使用图 # with g.as_default(): # a = tf.constant(5.0) # b = tf.constant(6.0) # sum1 = tf.add(a, b) # with tf.Session() as sess: # print(sess.run(sum1)) def tensor(): """ 张量 :return: """ # 占位符 plt = tf.placeholder(tf.float32, [None, 2]) print(plt) # 使用set_shape 确定形状为[3,2] plt.set_shape([3, 2]) print(plt) # 静态形状张量一旦固定,则不能再次设置了,而且元素的个数和纬度要一致 # plt.set_shape([4, 2]) # print(plt) # 如果想再次设置形状,可以考虑使用动态张量。生成一个新的张量 # 但是要注意: [2,3] 可以变成[3,2],[6,1,1] 但是不能[3,3] 因为特征值数量一共6个,没办法变成9个 plt_reshape = tf.reshape(plt, [6, 1, 1]) print(plt_reshape) def tensor_op(): """ 张量的操作 :return: """ # 全是0 的张量 zero = tf.zeros(shape=[3, 4], dtype=tf.float32) # 全是1 的张量 print(zero.eval()) zero = tf.ones(shape=[3, 4], dtype=tf.float32) print(zero.eval()) # 指定张量 cons = tf.constant(value=[5, 1], shape=[3, 3], dtype=tf.float32) print(cons.eval()) # 创建随机张量 random = tf.random_normal(shape=[3, 3], mean=6, stddev=1.0, dtype=tf.float32) print(random.eval()) # 张量的类型转换 c = tf.cast(random, tf.float32) print(c.eval()) # 张量的合并。 列拼装 cc = tf.concat([cons, c], axis=1) print(cc.eval()) def variable(): """ 变量 :return: """ # 初始化一个变量 random = tf.random_normal([2, 3], mean=0, stddev=1.0) v1 = tf.Variable(random) print(v1) # 变量不能直接计算,必须先做显示的初始化操作 init_op = tf.global_variables_initializer() with tf.Session() as sess: sess.run(init_op) # 把程序的图,写入到事件文件 filewriter = tf.summary.FileWriter("./test", graph=sess.graph) print(sess.run(v1)) def liner(): """ 手动实现线性回归 :return: """ with tf.variable_scope("a"): # 准备数据 x 100 个样本 1 个特征 假设 目标值 y = 0.7x + 0.8 x = tf.random_normal([100, 1], mean=1.75, stddev=0.5) # 建立线性回归模型 1特征1权重1偏置 y = wx + b y_true = tf.matmul(x, [[0.7]]) + 0.8 # 随机初始化权重weight 和偏置bias weight = tf.Variable(tf.random_normal([1, 1], mean=0, stddev=1), name='w') b = tf.Variable(0.0, name='b') with tf.variable_scope("b"): # 求预测predict y_pre = tf.matmul(x, weight) + b # 计算损失loss loss = tf.reduce_mean(tf.square(y_true - y_pre)) # 梯度下降优化损失 learn_rate: 0-1. 返回一个op train_op = tf.train.GradientDescentOptimizer(0.2).minimize(loss) # 通过会话,循环训练 运行程序[变量初始化global] init_op = tf.global_variables_initializer() # 收集tensor tf.summary.scalar("losses", loss) tf.summary.histogram("weight", weight) # 合并 merged_op = tf.summary.merge_all() # 定义一个保存模型的实例 saver = tf.train.Saver(var_list=None, max_to_keep=5) with tf.Session() as sess: sess.run(init_op) print("初始w 和 b:", weight.eval(), b.eval()) filewriter = tf.summary.FileWriter('./test/', sess.graph) # 加载模型,覆盖模型当中随机定义的参数,从检查点开始运行 if os.path.exists("./ckpt/checkpoint"): saver.restore(sess, "./ckpt/model") for i in range(200): sess.run(train_op) # 运行合并的merge_op summary = sess.run(merged_op) filewriter.add_summary(summary, i) print("第{}次训练完之后的w 和 b: ".format(i), weight.eval(), b.eval()) saver.save(sess, "./ckpt/model") if __name__ == '__main__': liner()
Python_ML-Day04: 深度学习、Tensorflow
最新推荐文章于 2023-04-17 12:18:14 发布