<TensorFlow学习使用P1>——《TensorFlow教程》

news2024/11/26 0:46:54

一、TensorFlow概述

前言:
本文中一些TensorFlow综合案例的代码逻辑一般正常,在本地均可运行。如有代码复现运行失败,原因如下:
(1)运行环境配置可能有误。
(2)由于一些数据集存储空间较大,这里没有上传,代码可能无法加载相应文件。
(3)涉及到一些存储、加载的文件路径没有填写正确等。
(4)本博客中涉及到TensorFlow的环境安装,这里没有详细展开,读者如有遇到环境安装问题,可通过开源社区互助解决。


  • 读者可注意比对Pycharm中,左上部分的project文件区域,查看是否有相对应的文件或文件夹。作者这里入过坑,但经过不断修改,所有代码已验证均可正常运行。
  • 作者在此向无数为科学研究及应用、推动人类文明向前发展,所付出心血的前辈们致敬!祝福开源世界蒸蒸日上,让知识不再因壁垒而淡去星辉!

1.什么是TensorFlow

在这里插入图片描述
TensorFlow的发展历史:
在这里插入图片描述

2.TensorFlow的特点

在这里插入图片描述

3.TensorFlow的安装

在这里插入图片描述
TensorFlow离线包地址链接:https://pypi.org/project/tensorflow/#files
在这里插入图片描述

4.TensorFlow的使用

示例1:使用TensorFlow打印“helloworld”
在这里插入图片描述

# 01_helloworld.py
# tensorflow版本的helloworld
#这是TensorFlow 1.*版本支持的Session
# import tensorflow as tf
# print(tf.version)

#因为 TensorFlow 2.0 引入了重大改变,
# 其中最显著的是引入了基于 eager execution 的默认执行模式,
# 这意味着不再需要显式的会话(session)和图构建过程。
#所以需要使用下列方式导入,以使用Session
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

hello = tf.constant("hello, world!") # 定义一个常量(张量)
sess = tf.Session() # 创建一个session, 用来执行操作
print(sess.run(hello)) # 调用session的run方法,执行hello操作,并打印结果
sess.close() # 关闭session

示例2:使用TensorFlow实现加法操作
在这里插入图片描述

# 02_add.py
# 张量相加的示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

a = tf.constant(5.0) # 张量a
b = tf.constant(1.0) # 张量b
c = tf.add(a, b) # 张量相加

with tf.Session() as sess:
    print(sess.run(c))

5.TensorFlow的体系结构

体系结构概述:
在这里插入图片描述

5.1单机模式与分布式模式

在这里插入图片描述

5.2后端逻辑层次

在这里插入图片描述

6.TensorFlow基本概念

张量:
在这里插入图片描述
数据流:
在这里插入图片描述

操作:
在这里插入图片描述
图和会话:
在这里插入图片描述
变量和占位符:
在这里插入图片描述

二、TensorFlow基本操作

1.图和会话操作

1.1什么是图

在这里插入图片描述
在这里插入图片描述
会话的操作:
在这里插入图片描述

示例3:使用TensorFlow查看图对象、指定会话运行某个图
在这里插入图片描述

# 03_graph_attr.py
# 查看默认图的属性
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

a = tf.constant(5.0)
print(a)
b = tf.constant(1.0)
c = tf.add(a, b)

graph = tf.get_default_graph() # 获取默认的图
print("graph:",graph)

# 新创建一个图
graph2 = tf.Graph()
print("graph2:",graph2)
with graph2.as_default(): # 设置为默认图
    d = tf.constant(11.0) # 操作d属于graph2

with tf.Session(graph=graph2) as sess: # 指定执行graph2
    # print(sess.run(c)) # 报错,因为c没有在默认graph2中
    print(sess.run(d))
    print(a.graph) # 打印张量的graph属性
    print(c.graph) # 打印c操作的graph属性
    print(sess.graph) # 打印session的graph属性

会话常见的错误及原因:
在这里插入图片描述

1.2张量的属性及基本运算

张量的阶与形状:
在这里插入图片描述
张量的数据类型:
在这里插入图片描述
示例4:使用TensorFlow查看张量属性
在这里插入图片描述

# 04_tensor_attr.py
# 查看张量属性示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

a = tf.constant(5.0)  # 标量

with tf.Session() as sess:
    print(sess.run(a))
    print("name:", a.name)  # name属性
    print("dtype:", a.dtype)  # dtype
    print("shape:", a.shape)  # shape
    print("op:", a.op)  # op
    print("graph:", a.graph)  # graph

示例5:使用TensorFlow创建张量
在这里插入图片描述

# 05_create_tensor.py
# 创建张量示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

# 创建值全为0的张量
tensor_zeros = tf.zeros(shape=[2,3], # 2行3列
                        dtype="float32") # 类型
# 创建值全为1的张量
tensor_ones = tf.ones(shape=[2,3], dtype="float32")
# 创建正态分布随机张量
tensor_nd = tf.random_normal(shape=[10], #一维,10个元素
                             mean=1.7, # 中位数
                             stddev=0.2,
                             dtype="float32")
# 创建形状和tensor_ones一样,值全为0的张量
tensor_zeros_like = tf.zeros_like(tensor_ones)

with tf.Session() as sess:
    print(tensor_zeros.eval()) # eval表示在session中执行计算
    print(tensor_ones.eval())
    print(tensor_nd.eval())
    print(tensor_zeros_like.eval())

1.3张量类型转换

在这里插入图片描述
示例6:使用TensorFlow进行张量类型转换
在这里插入图片描述

# 06_cast.py
# 张量类型转换示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

tensor_ones = tf.ones(shape=[2,3], dtype="int32")
tensor_float = tf.constant([1.1, 2.2, 3.3])

with tf.Session() as sess:
    print(tf.cast(tensor_ones, tf.float32).eval()) # 将tensor_ones转换为浮点型并打印
    # print(tf.cast(tensor_float, tf.string).eval())

1.4占位符

在这里插入图片描述
示例7:占位符的使用
在这里插入图片描述

# 07_placeholder.py
# 占位符使用示例:占位符在使用时,必须传入参数

#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

# 定义两个占位符
plhd = tf.placeholder(tf.float32, [2, 3]) # 定义2行3列的占位符
plhd2 = tf.placeholder(tf.float32, [None, 3]) # N行3列占位符
plhd3 = tf.placeholder(tf.float32, [None, 4])

with tf.Session() as sess:
    d = [[1, 2, 3],
         [4, 5, 6]]
    print(sess.run(plhd, feed_dict={plhd:d})) # 执行占位符操作,需要传入数据
    print(sess.run(plhd2, feed_dict={plhd2:d})) # 定义为N行3列,执行时传入2行3列
    # print(sess.run(plhd3, feed_dict={plhd3:d})) # 定义为N行4列,执行时传入2行3列

1.5张量形状改变

在这里插入图片描述
示例8:张量形状改变
在这里插入图片描述

# 08_reshape.py
# 张量形状改变
# 静态形状:初始形状,只能设置一次,不能跨阶设置
# 动态形状:运行时的形状,可以多次设置,可以跨阶设置,但元素总数要一致
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

pld = tf.placeholder(tf.float32, [None, 3])

pld.set_shape([4, 3]) # 设置静态形状,一旦固定就不能再改变
print(pld)
# pld.set_shape([3, 3]) # 报错

# 设置张量的动态形状,实际是创建一个新的张量
new_pld = tf.reshape(pld, [3, 4]) # 设置动态形状
print(new_pld)

new_pld = tf.reshape(pld, [2, 6]) # 多次设置动态形状
print(new_pld)

# new_pld = tf.reshape(pld, [2, 4]) # 报错,元素个数不匹配

with tf.Session() as sess:
    pass

1.6张量的数学计算

在这里插入图片描述
在这里插入图片描述
示例9:张量的数学计算
在这里插入图片描述

# 09_math_oper.py
# 张量的数学计算示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

x = tf.constant([[1, 2],
                 [3, 4]], dtype=tf.float32)
y = tf.constant([[4, 3],
                 [3, 2]], dtype=tf.float32)

x_add_y = tf.add(x, y)  # 张量相加
x_mul_y = tf.matmul(x, y) # 张量相乘(按照矩阵相乘的规则)
log_x = tf.log(x) # 求对数
x_sum_1 = tf.reduce_sum(x, axis=[0]) # 1-行方向 0-列方向

# 张量计算片段和
data = tf.constant([1,2,3,4,5,6,7,8,9,10], dtype=tf.float32)
segment_ids = tf.constant([0, 0, 0, 1, 1, 2, 2, 2, 2, 2], dtype=tf.int32)
x_seg_sum = tf.segment_sum(data, segment_ids)

with tf.Session() as sess:
    print(x_add_y.eval())
    print(x_mul_y.eval())
    print(log_x.eval())
    print(x_sum_1.eval())
    print(x_seg_sum.eval())

1.7变量

在这里插入图片描述
示例10:变量使用
在这里插入图片描述

# 10_variable.py
# 变量使用示例
"""
1. 变量是一种特殊的张量,变量中存的值是张量
2. 变量可以进行持久化保存,张量则不可
3. 变量使用之前,要进行显式初始化
"""
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

a = tf.constant([1, 2, 3, 4])
var = tf.Variable(tf.random_normal([2, 3], mean=0.0, stddev=1.0), #初始值
                  name="var")
# 变量操作执行之前,需要进行全局初始化(初始化也是一个op,需要在session的run方法中执行)
init_op = tf.global_variables_initializer()

with tf.Session() as sess:
    sess.run(init_op)
    print(sess.run([a, var]))

三、TensorFlow可视化

1.Tensorboard可视化

1.1什么是可视化

在这里插入图片描述
在这里插入图片描述

1.2启动Tensorboard

Windows环境下启动Tensorboard演示:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在Linux环境下可以直接使用:tensorboard --logdir=“文件路径”

例如:tensorboard --logdir=“PycharmProjects/tensorflow_study/summary/”

示例11:将图中的信息存入事件文件,并在tensorboard中显示示例
在这里插入图片描述

# 11_tensorboard_demo.py
# 将图中的信息存入事件文件,并在tensorboard中显示示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

# 创建一组操作
a = tf.constant([1, 2, 3, 4, 5]) # 普通张量
var = tf.Variable(tf.random_normal([2,3], mean=0.0, stddev=1.0),
                  name="var") #变量

b = tf.constant(3.0, name="a") #这里故意将python变量和tf的op名称取的不一致
c = tf.constant(4.0, name="b")
d = tf.add(b, c, name="add")

# 显式初始化
init_op = tf.global_variables_initializer()

with tf.Session() as sess:
    sess.run(init_op)
    #将当前session的graph信息写入事件文件
    fw = tf.summary.FileWriter("../summary/", graph=sess.graph)
    print(sess.run([a, var, d]))

在这里插入图片描述
摘要与事件文件操作:
在这里插入图片描述

四、TensorFlow综合案例——实现线性回归

在这里插入图片描述
在这里插入图片描述
示例12:使用TensorFlow实现线性回归
在这里插入图片描述

# 12_lr.py
# 线性回归示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()

# 第一步:创建样本数据
x = tf.random_normal([100, 1], mean=1.75, stddev=0.5, name="x_data")
y_true = tf.matmul(x, [[2.0]]) + 5.0  # 计算 y = 2x + 5

# 第二步:建立线性模型
## 初始化权重(随机数)和偏置(固定设置为0),计算wx+b得到预测值
weight = tf.Variable(tf.random_normal([1, 1], name="w"),
                     trainable=True)  # 训练过程中值是否允许变化
bias = tf.Variable(0.0, name="b", trainable=True)  # 偏置
y_predict = tf.matmul(x, weight) + bias  # 计算预测值

# 第三步:创建损失函数
loss = tf.reduce_mean(tf.square(y_true - y_predict))  # 均方差损失函数

# 第四步:使用梯度下降进行训练
train_op = tf.train.GradientDescentOptimizer(0.1).minimize(loss)

# 收集损失函数的值
tf.summary.scalar("losses", loss)
merged = tf.summary.merge_all()  # 合并摘要操作

init_op = tf.global_variables_initializer()
with tf.Session() as sess:
    sess.run(init_op)  # 执行初始化op

    # 打印初始权重和偏置
    print("weight:", weight.eval(), " bias:", bias.eval())

    # 指定事件文件并记录图的信息
    fw = tf.summary.FileWriter("../summary/", graph=sess.graph)

    # 循环训练
    for i in range(500):
        sess.run(train_op)  # 执行训练
        summary = sess.run(merged)  # 执行摘要合并操作
        fw.add_summary(summary, i)  # 写入事件文件

        print(i, ":", " weight:", weight.eval(), " bias:", bias.eval())

启动Tensorboard运行:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

五、TensorFlow数据读取

1.模型保存和加载

在这里插入图片描述模型保存和加载API:
在这里插入图片描述
示例13:线性回归的保存与加载
在这里插入图片描述
第一次训练:观察weight和bias的值
在这里插入图片描述
第二次训练:观察到weight和bias的初始值是第一次训练后的保存值!
在这里插入图片描述
继续训练,weight和bias的训练值将会更加接近预期值!

# 13_lrsaveload.py
# 线性回归示例,添加保存与加载模块
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
import os

# 第一步:创建样本数据
x = tf.random_normal([100, 1], mean=1.75, stddev=0.5, name="x_data")
y_true = tf.matmul(x, [[2.0]]) + 5.0  # 计算 y = 2x + 5

# 第二步:建立线性模型
## 初始化权重(随机数)和偏置(固定设置为0),计算wx+b得到预测值
weight = tf.Variable(tf.random_normal([1, 1], name="w"),
                     trainable=True)  # 训练过程中值是否允许变化
bias = tf.Variable(0.0, name="b", trainable=True)  # 偏置
y_predict = tf.matmul(x, weight) + bias  # 计算预测值

# 第三步:创建损失函数
loss = tf.reduce_mean(tf.square(y_true - y_predict))  # 均方差损失函数

# 第四步:使用梯度下降进行训练
train_op = tf.train.GradientDescentOptimizer(0.1).minimize(loss)

# 收集损失函数的值
tf.summary.scalar("losses", loss)
merged = tf.summary.merge_all()  # 合并摘要操作

init_op = tf.global_variables_initializer()

saver = tf.train.Saver() #实例化一个saver

with tf.Session() as sess:
    sess.run(init_op)  # 执行初始化op

    # 打印初始权重和偏置
    print("weight:", weight.eval(), " bias:", bias.eval())

    # 指定事件文件并记录图的信息
    fw = tf.summary.FileWriter("../summary/", graph=sess.graph)

    #训练之前,检查是否已经有模型保存。如果有,则加载
    if os.path.exists("../model/linear_model/checkpoint"):
        saver.restore(sess,"../model/linear_model/")
    # 循环训练
    for i in range(200):
        sess.run(train_op)  # 执行训练
        summary = sess.run(merged)  # 执行摘要合并操作
        fw.add_summary(summary, i)  # 写入事件文件

        print(i, ":", " weight:", weight.eval(), " bias:", bias.eval())

    #训练完成,保存模型
    saver.save(sess,"../model/linear_model/")

2.数据读取

2.1文件读取机制

在这里插入图片描述
在这里插入图片描述

2.2文件读取API

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

六、TensorFlow数据读取案例

1.CSV文件读取

示例14:csv文件读取
在这里插入图片描述
注:
(1)上述因为在读取的时候是做了随机化处理,读取顺序被打乱了。
(2)第一个数组为所有文本文件的第一列,第二个数组为所有文本文件的第二列。
(3)虽然读取顺序被打乱,但是第一列的数据和第二列的数据是一一对应的。
更改批次大小:
在这里插入图片描述

# 01_csv_reader.py
# CSV文件读取示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
import os


def csv_read(filelist):  # 从csv样本文件中读取数据
    # 构建文件队列
    file_queue = tf.train.string_input_producer(filelist)
    # 定义reader
    reader = tf.TextLineReader()
    k, v = reader.read(file_queue)  # 读取,返回文件名称、数据
    # 解码
    records = [["None"], ["None"]]
    example, label = tf.decode_csv(v, record_defaults=records)
    # 批处理
    example_bat, label_bat = tf.train.batch([example, label],  # 参与批处理的数据
                                            #batch_size=9,  # 批次大小
                                            batch_size=4,  # 批次大小
                                            num_threads=1)  # 线程数量
    return example_bat, label_bat


if __name__ == "__main__":
    # 构建文件列表
    dir_name = "../test_data/"
    file_names = os.listdir(dir_name)  # 列出目录下所有的文件
    file_list = []
    for f in file_names:
        # 将目录名称、文件名称拼接称完整路径,并添加到文件列表
        file_list.append(os.path.join(dir_name, f))

    example, label = csv_read(file_list)  # 调用自定义函数,读取指定文件列表中的数据

    # 开启Session,执行
    with tf.Session() as sess:
        coord = tf.train.Coordinator()  # 定义线程协调器
        threads = tf.train.start_queue_runners(sess, coord=coord)
        print(sess.run([example, label]))  # 执行操作

        # 等待线程停止,并回收资源
        coord.request_stop()
        coord.join(threads)

2.图片文件的读取

2.1图片读取API

在这里插入图片描述
在这里插入图片描述
示例15:图像文件读取
在这里插入图片描述

# 02_img_reader.py
# 图像样本读取示例
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
import os

# 图像样本读取函数
def img_read(filelist):
    # 构建文件队列
    file_queue = tf.train.string_input_producer(filelist)
    # 定义reader
    reader = tf.WholeFileReader()
    k, v = reader.read(file_queue) # 读取整个文件内容
    # 解码
    img = tf.image.decode_jpeg(v)
    # 批处理
    img_resized = tf.image.resize(img, [200, 200]) # 将图像设置成200*200大小
    img_resized.set_shape([200, 200, 3]) # 固定样本形状,批处理时对数据形状有要求
    img_bat = tf.train.batch([img_resized],
                             batch_size=10,
                             num_threads=1)
    return img_bat

if __name__ == "__main__":
    # 构建文件列表
    dir_name = "../test_img/"
    file_names = os.listdir(dir_name)
    file_list = []
    for f in file_names:
        # 将目录名、文件名拼接成完整路径放入文件列表中
        file_list.append(os.path.join(dir_name, f))

    imgs = img_read(file_list)

    with tf.Session() as sess:
        coord = tf.train.Coordinator() # 线程协调器
        threads = tf.train.start_queue_runners(sess, coord=coord)
        result = imgs.eval() # 调用函数,分批次读取样本

        # 等待线程结束,并回收资源
        coord.request_stop()
        coord.join(threads)

# 显示图片
import matplotlib.pyplot as plt

plt.figure("Img Show", facecolor="lightgray")

for i in range(10):  # 循环显示读取到的样本(批次读取,所以有多个样本)
    plt.subplot(2, 5, i+1) # 显示子图, 2行5列的第i+1个子图
    plt.xticks([])
    plt.yticks([])
    plt.imshow(result[i].astype("int32"))

plt.tight_layout()
plt.show()

3.深度学习平台数据读取总结

(1)深度学习平台对数据的读取,需要能够实现快速读取,因为训练的样本可能很多。
(2)需要能够实现随机的读取, 消除样本的顺序,对模型产生的影响。
(3)需要能够实现批量读取,分批处理。

七、TensorFlow综合案例——实现手写体识别

注:这里使用的是全连接模型作为分类器

1.MNIST数据集

在这里插入图片描述
MNIST数据集地址链接:http://yann.lecun.com/exdb/mnist/
任务目标:
在这里插入图片描述

2.网络结构

在这里插入图片描述
(输入:28x28)

3.相关API

在这里插入图片描述
示例16:mnist数据集手写数字识别
一些bug原因:
在这里插入图片描述
解决办法:
注:由于目前TensorFlow的最新版本是2.x,因此在代码中有一些bug是新版本不再支持1.x版本的调用方式。

“如果你正在使用的是 TensorFlow 2.x 版本,tensorflow.examples 已经不存在。TensorFlow 2.x 重构了许多组件,并引入了 Keras 作为主要接口,tensorflow.examples 中的许多内容已经迁移到其他位置或被新的 API 替代。”

解决办法:
(1)使用新的调用方式
(2)降低TensorFlow版本
(3)添加需要的代码包等
本次采用添加需要的代码包作为演示:
在这里插入图片描述
训练结果:
(这里是随机选取两张图片进行训练预测)
预测数字:
在这里插入图片描述
另一个预测数字:
在这里插入图片描述
注释训练模块代码,直接使用前次训练模型进行预测:
在这里插入图片描述
另一个预测数字:
在这里插入图片描述
可以看出,另一个数字预测有失精确,但多加训练和调整参数/权重,可以提高精确度!

# 03_mnist.py
# 手写体识别案例
# 模型:全连接模型
#import tensorflow as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
#from tensorflow.examples.tutorials.mnist import input_data
import input_data
import pylab

# 定义样本读取对象
mnist = input_data.read_data_sets("MNIST_data/",  # 数据集所在目录
                                  one_hot=True)  # 标签是否采用独热编码
# 定义占位符,用于表图像数据、标签
x = tf.placeholder(tf.float32, [None, 784])  # 图像数据,N行784列
y = tf.placeholder(tf.float32, [None, 10])  # 标签(图像真实类别), N行784列

# 定义权重、偏置
w = tf.Variable(tf.random_normal([784, 10]))  # 权重,784行10列
b = tf.Variable(tf.zeros([10]))  # 偏置, 10个偏置

# 构建模型,计算预测结果
pred_y = tf.nn.softmax(tf.matmul(x, w) + b)
# 损失函数
cross_entropy = -tf.reduce_sum(y * tf.log(pred_y), reduction_indices=1)
cost = tf.reduce_mean(cross_entropy)  # 求均值
# 梯度下降优化器
optimizer = tf.train.GradientDescentOptimizer(0.01).minimize(cost)

batch_size = 100  # 批次大小
saver = tf.train.Saver()  # saver
model_path = "../model/mnist/mnist_model.ckpt"  # 模型路径

with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())  # 初始化
    # 开始训练
    for epoch in range(200):
        # 计算总批次
        total_batch = int(mnist.train.num_examples / batch_size)
        avg_cost = 0.0
        for i in range(total_batch):
            # 从训练集读取一个批次的样本
            batch_xs, batch_ys = mnist.train.next_batch(batch_size)
            params = {x: batch_xs, y: batch_ys}  # 参数字典
            o, c = sess.run([optimizer, cost],  # 执行的op
                            feed_dict=params)  # 喂入参数
            avg_cost += (c / total_batch)  # 计算平均损失值
        print("epoch:%d, cost=%.9f" % (epoch + 1, avg_cost))
    print("训练结束.")
    # 模型评估
    # 比较预测结果和真实结果,返回布尔类型的数组
    correct_pred = tf.equal(tf.argmax(pred_y, 1),  # 求预测结果中最大值的索引
                            tf.argmax(y, 1))  # 求真实结果中最大的索引
    # 将布尔类型数组转换为浮点数,并计算准确率
    # 因为计算均值、准确率公式相同,所以调用计算均值的函数计算准确率
    accuracy = tf.reduce_mean(tf.cast(correct_pred, tf.float32))
    print("accuracy:", accuracy.eval({x: mnist.test.images,  # 测试集下的图像数据
                                      y: mnist.test.labels}))  # 测试集下图像的真实类别
    # 保存模型
    save_path = saver.save(sess, model_path)
    print("模型已保存:", save_path)

#注释训练模块代码,使用训练模型进行直接预测检验
'''
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())  # 初始化
    # 开始训练
    for epoch in range(200):
        # 计算总批次
        total_batch = int(mnist.train.num_examples / batch_size)
        avg_cost = 0.0
        for i in range(total_batch):
            # 从训练集读取一个批次的样本
            batch_xs, batch_ys = mnist.train.next_batch(batch_size)
            params = {x: batch_xs, y: batch_ys}  # 参数字典
            o, c = sess.run([optimizer, cost],  # 执行的op
                            feed_dict=params)  # 喂入参数
            avg_cost += (c / total_batch)  # 计算平均损失值
        print("epoch:%d, cost=%.9f" % (epoch + 1, avg_cost))
    print("训练结束.")
    # 模型评估
    # 比较预测结果和真实结果,返回布尔类型的数组
    correct_pred = tf.equal(tf.argmax(pred_y, 1),  # 求预测结果中最大值的索引
                            tf.argmax(y, 1))  # 求真实结果中最大的索引
    # 将布尔类型数组转换为浮点数,并计算准确率
    # 因为计算均值、准确率公式相同,所以调用计算均值的函数计算准确率
    accuracy = tf.reduce_mean(tf.cast(correct_pred, tf.float32))
    print("accuracy:", accuracy.eval({x: mnist.test.images,  # 测试集下的图像数据
                                      y: mnist.test.labels}))  # 测试集下图像的真实类别
    # 保存模型
    save_path = saver.save(sess, model_path)
    print("模型已保存:", save_path)
'''
# 从测试集中随机读取2张图像,执行预测
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    saver.restore(sess, model_path)  # 加载模型

    # 从测试集中读取样本
    batch_xs, batch_ys = mnist.test.next_batch(2)
    output = tf.argmax(pred_y, 1)  # 直接取出预测结果中的最大值

    output_val, predv = sess.run([output, pred_y],  # 执行的op
                                 feed_dict={x: batch_xs})  # 预测,所以不需要传入标签
    print("预测最终结果:\n", output_val, "\n")
    print("真实结果:\n", batch_ys, "\n")
    print("预测概率:\n", predv, "\n")

    # 显示图片
    im = batch_xs[0]  # 第一个测试样本
    im = im.reshape(-1, 28)  # 28列,-1表示经过计算的值
    pylab.imshow(im)
    pylab.show()

    im = batch_xs[1]  # 第二个测试样本
    im = im.reshape(-1, 28)  # 28列,-1表示经过计算的值
    pylab.imshow(im)
    pylab.show()

八、TensorFlow综合案例——实现服饰识别

注:这里开始采用卷积神经网络进行识别

1.数据集介绍

在这里插入图片描述
任务目标:
在这里插入图片描述

2.网络结构

在这里插入图片描述
在这里插入图片描述

3.具体实现

这里采用面向对象的方式实现:
在这里插入图片描述
在这里插入图片描述
一些bug说明:

代码的逻辑一般是正确的,运行失败是TensorFlow2.x版本不再支持contrib,
解决尝试:
1.降低TensorFlow版本(这个不可行,目前已无法直接pip install 1.x版本)
2.使用contrib迁移到2.x的版本的APl:keras 重新编写代码,(这种方式需要重新编写代码,使用新的API编写方式。)
在这里插入图片描述
在这里插入图片描述

# 04_fashion_mnist.py
# 使用卷积神经网络实现服饰识别
#import tensorflow  as tf
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
from tensorflow.contrib.learn.python.learn.datasets.mnist import read_data_sets

# 定义FashionMnist类
class FashionMnist():
    out_features1 = 12 # 第一组卷积层输出通道数量(即第一个卷积层卷积核数)
    out_features2 = 24 # 第二组卷积层输出通道数量(即第二个卷积层卷积核数)
    con_neurons = 512 # 全连接层神经元数量

    def __init__(self, path):
        """
        构造方法
        :param path: 指定数据集目录
        """
        self.sess = tf.Session()
        self.data = read_data_sets(path, one_hot=True)

    def init_weight_variable(self, shape):
        """
        根据指定形状初始化权重
        :param shape: 指定要初始化的变量的形状
        :return: 返回经过初始化的变量
        """
        inital = tf.truncated_normal(shape, stddev=0.1) # 截尾正态分布
        return tf.Variable(inital)

    def init_bias_variable(self, shape):
        """
        初始化偏置
        :param shape: 指定要初始化的变量的形状
        :return: 返回经过初始化的变量
        """
        inital = tf.constant(1.0, shape=shape)
        return tf.Variable(inital)

    def conv2d(self, x, w):
        """
        二维卷积方法
        :param x: 原始数据
        :param w: 卷积核
        :return: 返回卷积运算的结果
        """
        # 卷积核: [高度, 宽度, 输入通道数, 输出通道数]
        return tf.nn.conv2d(x, # 原始数据
                            w, # 卷积核
                            strides=[1, 1, 1, 1], # 各维度上的步长值
                            padding="SAME") # 输入矩阵和输出矩阵大小一样

    def max_pool_2x2(self, x):
        """
        定义池化方法
        :param x: 原始数据
        :return: 池化计算结果
        """
        return tf.nn.max_pool(x,
                              ksize=[1, 2, 2, 1], # 池化区域大小
                              strides=[1, 2, 2, 1], # 各个维度上的步长值
                              padding="SAME")

    def create_conv_pool_layer(self, input, input_features, out_features):
        """
        定义卷积、激活、池化层
        :param input: 原始数据
        :param input_features:输入特征数量
        :param out_features: 输出特征数量
        :return: 卷积、激活、池化层运算结果
        """
        filter = self.init_weight_variable([5, 5, input_features, out_features]) # 卷积核
        b_conv = self.init_bias_variable([out_features]) # 偏置,卷积有多少输出就有多少个偏置
        h_conv = tf.nn.relu(self.conv2d(input, filter) + b_conv) # 卷积,激活运算
        h_pool = self.max_pool_2x2(h_conv) # 对卷积激活运算结果做池化
        return h_pool

    def create_fc_layer(self, h_pool_flat, input_features, con_neurons):
        """
        创建全连接层
        :param h_pool_flat: 输入数据,经过拉伸后的一维张量
        :param input_features: 输入特征数量
        :param con_neurons: 神经元数量(输出特征数量)
        :return: 经过全连接计算后的结果
        """
        w_fc = self.init_weight_variable([input_features, con_neurons]) # 权重
        b_fc = self.init_bias_variable([con_neurons]) # 偏置
        h_fc1 = tf.nn.relu(tf.matmul(h_pool_flat, w_fc) + b_fc) # 计算wx+b并做激活
        return h_fc1

    def build(self):
        """
        组建CNN
        :return:
        """
        # 定义输入数据、标签数据的占位符
        self.x = tf.placeholder(tf.float32, shape=[None, 784])
        x_image = tf.reshape(self.x, [-1, 28, 28, 1]) # 变维成28*28单通道图像数据
        self.y_ = tf.placeholder(tf.float32, shape=[None, 10]) # 标签, N个样本,每个样本10个类别对应的概率

        # 第一组卷积池化
        h_pool1 = self.create_conv_pool_layer(x_image, 1, self.out_features1)

        # 第二层卷积池化
        h_pool2 = self.create_conv_pool_layer(h_pool1, # 以上一个卷积池化层的输出作为输入
                                              self.out_features1, # 输入特征数量,为上一层输出特征数量
                                              self.out_features2) # 输出特征数量
        # 全连接
        h_pool2_flat_features = 7 * 7 * self.out_features2 # 计算特征点数量
        h_pool2_flat = tf.reshape(h_pool2, [-1, h_pool2_flat_features]) # 拉伸成一维
        h_fc = self.create_fc_layer(h_pool2_flat, # 输入
                                    h_pool2_flat_features, # 输入特征数量
                                    self.con_neurons) # 输出特征数量
        # dropout(通过随机丢弃一定比例神经元参数更新,防止过拟合)
        self.keep_prob = tf.placeholder("float") # 保存率
        h_fc1_drop = tf.nn.dropout(h_fc, self.keep_prob)

        # 输出层
        w_fc = self.init_weight_variable([self.con_neurons, 10]) # 512行10列
        b_fc = self.init_bias_variable([10]) # 10个偏置
        y_conv = tf.matmul(h_fc1_drop, w_fc) + b_fc # 计算wx+b

        # 计算准确率
        correct_prediction = tf.equal(tf.argmax(y_conv, 1),
                                      tf.argmax(self.y_, 1))
        self.accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))

        # 损失函数
        loss_func = tf.nn.softmax_cross_entropy_with_logits(labels=self.y_, # 真实值
                                                            logits=y_conv) # 预测值
        cross_entropy = tf.reduce_mean(loss_func)

        # 优化器
        optimizer = tf.train.AdamOptimizer(0.001)
        self.train_step = optimizer.minimize(cross_entropy)

    def train(self):
        self.sess.run(tf.global_variables_initializer())
        batch_size = 100 # 批次大小
        print("begin training...")

        for i in range(10):
            total_batch = int(self.data.train.num_examples / batch_size) # 计算批次数量

            for j in range(total_batch):
                batch = self.data.train.next_batch(batch_size) # 获取一个批次样本
                params = {self.x: batch[0],  # 图像
                          self.y_: batch[1], # 标签
                          self.keep_prob:0.5} # 计算丢弃率

                t, acc = self.sess.run([self.train_step, self.accuracy], # 执行的op
                                       params)

                if j % 100 == 0:
                    print("i: %d, j: %d  acc: %f" % (i, j, acc))

    def eval(self, x, y, keep_prob):
        params = {self.x:x, self.y_:y, self.keep_prob:0.5}
        test_acc = self.sess.run(self.accuracy, params) # 计算准确率
        print("Test Accuracy: %f" % test_acc)
        return test_acc

    def close(self):
        self.sess.close()

if __name__ == "__main__":
    mnist = FashionMnist("fashion_mnist/")
    mnist.build() # 组件网络
    mnist.train() # 训练

    # 评估
    xs, ys = mnist.data.test.next_batch(100)
    mnist.eval(xs, ys, 0.5)
    mnist.close()


后记:
●本博客基于B站开源学习资源,是作者学习的笔记记录,仅用于学习交流,不做任何商业用途!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1557422.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

算法学习——LeetCode力扣图论篇2

算法学习——LeetCode力扣图论篇2 1020. 飞地的数量 1020. 飞地的数量 - 力扣(LeetCode) 描述 给你一个大小为 m x n 的二进制矩阵 grid ,其中 0 表示一个海洋单元格、1 表示一个陆地单元格。 一次 移动 是指从一个陆地单元格走到另一个相…

实施阶段(2024年3月)

本次探究的项目化学习主题为:校内订餐系统的分析与设计 【主题情境说明】 社会大背景:国家颁发《“健康中国2030”规划纲要》,尤其关注青少年儿童膳食质量,明确提出要加强孩子食育教育,家庭、学校和社会需要共建健康…

Linux系统---如何理解Linux中的文件系统

顾得泉:个人主页 个人专栏:《Linux操作系统》 《C从入门到精通》 《LeedCode刷题》 键盘敲烂,年薪百万! 一、理解文件系统 1.ls与stat 我们使用ls -l的时候看到的除了看到文件名,还看到了文件元数据。 每行包含7列…

【一站式学会Kotlin】第一节 kotlin 介绍

作者介绍: 百度资深Android工程师T6,在百度任职7年半。 目前:成立赵小灰代码工作室,欢迎大家找我开发Android、微信小程序、鸿蒙项目。 前些天发现了一个巨牛的人工智能学习网站,通俗易懂,风趣幽默。给大家…

Unity 基于Rigidbody2D模块的角色移动

制作好站立和移动的动画后 控制器设计 站立 移动 角色移动代码如下: using System.Collections; using System.Collections.Generic; using Unity.VisualScripting; using UnityEngine;public class p1_c : MonoBehaviour {// 获取动画组件private Animator …

【c++】简单的日期计算器

🔥个人主页:Quitecoder 🔥专栏:c笔记仓 朋友们大家好啊,在我们学习了默认成员函数后,我们本节内容来完成知识的实践,来实现一个简易的日期计算器 目录 头文件声明函数函数的实现1.全缺省默认构…

TASKPROMPTER

baseline模型的预训练权重就有1.6G! 多吓人呐,当时我就暂停下载了,不建议复现

[Flutter]打包IPA

1.直接使用Xcode运行iOS工程 不用flutter构建,在Xcode中是可以独立进行构建运行和打包发布的。 1).运行项目 先将flutter的build清理 $ flutter clean $ flutter pub get 然后立即用XCode打开iOS工程运行 运行会报错: error: The sandbox is not …

gpt-llm-trainer 出炉

每周跟踪AI热点新闻动向和震撼发展 想要探索生成式人工智能的前沿进展吗?订阅我们的简报,深入解析最新的技术突破、实际应用案例和未来的趋势。与全球数同行一同,从行业内部的深度分析和实用指南中受益。不要错过这个机会,成为AI领…

ML-Decoder: Scalable and Versatile Classification Head

1、引言 论文链接:https://openaccess.thecvf.com/content/WACV2023/papers/Ridnik_ML-Decoder_Scalable_and_Versatile_Classification_Head_WACV_2023_paper.pdf 因为 transformer 解码器分类头[1] 在少类别多标签分类数据集上表现得很好,但由于其查询…

【应用层协议原理】

文章目录 第二章 应用层2.1 应用层协议原理2.1.1 网络应用的体系结构2.1.2 客户-服务器(C/S)体系结构2.1.3 对等体(P2P)体系结构2.2.4 C/S和P2P体系结构的混合体2.2.5 进程通信问题1:对进程进行编址(addres…

厦门攸信技术亮相新技术研讨会,展现物流自动化解决方案新高度!

今日,厦门攸信信息技术有限公司受邀参加了一场备受行业关注的电子制造高端盛会——一步步新技术研讨会,凭借卓越的智能制造与物流自动化技术在会议中大放异彩。作为一家引领行业发展的企业,厦门攸信技术不仅展示了其深厚的技术底蕴&#xff0…

算法之美:堆排序原理剖析及应用案例分解实现

这段时间持续更新关于“二叉树”的专栏文章,关心的小伙伴们对于二叉树的基本原理已经有了初步的了解。接下来,我将会更深入地探究二叉树的原理,并且展示如何将这些原理应用到更广泛的场景中去。文章将延续前面文章的风格,尽量精炼…

数据结构 - 图

参考链接:数据结构:图(Graph)【详解】_图数据结构-CSDN博客 图的定义 图(Graph)是由顶点的有穷非空集合 V ( G ) 和顶点之间边的集合 E ( G ) 组成,通常表示为: G ( V , E ) ,其中, G 表示个图, V 是图 G…

深入理解 Hadoop 上的 Hive 查询执行流程

在 Hadoop 生态系统中,Hive 是一个重要的分支,它构建在 Hadoop 之上,提供了一个开源的数据仓库系统。它的主要功能是查询和分析存储在 Hadoop 文件中的大型数据集,包括结构化和半结构化数据。Hive 在数据查询、分析和汇总方面发挥…

Linux(CentOS7)安装 MySQL8

目录 下载 上传 解压 创建配置文件 初始化 MySQL 服务 启动 MySQL 服务 连接 MySQL 创建软链接 下载 官方地址: MySQL :: Download MySQL Community Serverhttps://dev.mysql.com/downloads/mysql/选择版本前需先看一下服务器的 glibc 版本 ldd --versio…

计算机视觉之三维重建(5)---双目立体视觉

文章目录 一、平行视图1.1 示意图1.2 平行视图的基础矩阵1.3 平行视图的极几何1.4 平行视图的三角测量 二、图像校正三、对应点问题3.1 相关匹配法3.2 归一化相关匹配法3.3 窗口问题3.4 相关法存在的问题3.5 约束问题 一、平行视图 1.1 示意图 如下图即是一个平行视图。特点&a…

基于Apriori关联规则的电影推荐系统(python实现)

基于Apriori关联规则的电影推荐系统 1、效果图 2、算法原理 Apriori算法是一种用于挖掘关联规则的频繁项集算法,它采用逐层搜索的迭代方法来发现数据库中项集之间的关系并形成规则。 其核心思想是利用Apriori性质来压缩搜索空间,即如果一个项集是非频繁的,那么它的所有父…

结构体类型,结构体变量的创建和初始化 以及结构中存在的内存对齐

一般结构体类型的声明 struct 结构体类型名 { member-list; //成员表列 }variable-list; //变量表列 例如描述⼀个学⽣: struct Stu { char name[20]; //名字 int age; //年龄 char sex[5]; //性别 }; //结构体变量的初始化 int main() { S…

Django详细教程(二) - 部门用户管理案例

文章目录 前言一、新建项目二、新建app三、设计表结构四、新建数据库五、新建静态文件六、部门管理1.部门展示2.部门添加3.部门删除4.部门编辑 七、模板继承八、用户管理1.辨析三种方法方法一:原始方法方法二:Form组件(简便)方法三:ModelForm…