第T7周:Tensorflow实现咖啡豆识别

目标

具体实现

(一)环境

语言环境 :Python 3.10
编 译 器: PyCharm
框 架:

(二)具体步骤
1. 使用GPU
复制代码
--------------------------utils.py-------------------
import tensorflow as tf  
import PIL  
import matplotlib.pyplot as plt  
  
  
def GPU_ON():  
    # 查询tensorflow版本  
    print("Tensorflow Version:", tf.__version__)  
  
    # 设置使用GPU  
    gpus = tf.config.list_physical_devices("GPU")  
    print(gpus)  
  
    if gpus:  
        gpu0 = gpus[0]  # 如果有多个GPU,仅使用第0个GPU  
        tf.config.experimental.set_memory_growth(gpu0, True)  # 设置GPU显存按需使用  
        tf.config.set_visible_devices([gpu0], "GPU")

使用GPU并查看数据

复制代码
import tensorflow as tf  
from tensorflow import keras  
import numpy as np  
import matplotlib.pyplot as plt  
import os, PIL, pathlib  
from utils import GPU_ON

GPU_ON()  
  
data_dir = "./datasets/coffee/"  
data_dir = pathlib.Path(data_dir)  
  
image_count = len(list(data_dir.glob("*/*.png")))  
print("图片总数量为:", image_count)
------------------
图片总数量为: 1200
2. 加载数据
复制代码
# 加载数据  
batch_size = 32  
img_height, img_width = 224, 224  
  
train_ds = tf.keras.preprocessing.image_dataset_from_directory(  
    data_dir,  
    validation_split=0.2,  
    subset="training",  
    seed=123,  
    image_size=(img_height, img_width),  
    batch_size=batch_size,  
)  
  
val_ds = tf.keras.preprocessing.image_dataset_from_directory(  
    data_dir,  
    validation_split=0.2,  
    subset="validation",  
    seed=123,  
    image_size=(img_height, img_width),  
    batch_size=batch_size,  
)
--------------------
Found 1200 files belonging to 4 classes.
Using 960 files for training.
Found 1200 files belonging to 4 classes.
Using 240 files for validation.

获取标签:

复制代码
# 获取标签  
class_names = train_ds.class_names  
print(class_names)
------------------
['Dark', 'Green', 'Light', 'Medium']

可视化数据:

复制代码
# 可视化数据  
plt.figure(figsize=(10, 10))  
for images, labels in train_ds.take(2):  
    for i in range(30):  
        ax = plt.subplot(5, 6, i+1)  
        plt.imshow(images[i].numpy().astype("uint8"))  
        plt.title(class_names[labels[i]])  
  
        plt.axis("off")  
plt.show()

检查一下数据:

复制代码
# 检查一下数据  
for image_batch, labels_batch in train_ds:  
    print(image_batch.shape)  
    print(labels_batch.shape)  
    break
----------------------------
(32, 224, 224, 3)
(32,)
**3.**配置数据集
复制代码
# 配置数据集  
AUTOTUNE = tf.data.AUTOTUNE  
train_ds = train_ds.cache().shuffle(1000).prefetch(buffer_size=AUTOTUNE)  
val_ds = val_ds.cache().prefetch(buffer_size=AUTOTUNE)  
  
normalization_layer = layers.experimental.preprocessing.Rescaling(1./255)  
train_ds = train_ds.map(lambda x, y: (normalization_layer(x), y))  
val_ds = val_ds.map(lambda x, y: (normalization_layer(x), y))  
  
image_batch, labels_batch = next(iter(train_ds))  
first_image = image_batch[0]  
  
# 查看归一化后的数据  
print(np.min(first_image), np.max(first_image))
--------------------
0.0 1.0
4.搭建VGG-16网络

本次准备直接调用官方模型

复制代码
# 搭建VGG-16网络模型  
model = tf.keras.applications.VGG16(weights="imagenet")  
print(model.summary())
-------------------------------
Downloading data from https://storage.googleapis.com/tensorflow/keras-applications/vgg16/vgg16_weights_tf_dim_ordering_tf_kernels.h5
553467096/553467096 [==============================] - 14s 0us/step
Model: "vgg16"
_________________________________________________________________
 Layer (type)                Output Shape              Param #   
=================================================================
 input_1 (InputLayer)        [(None, 224, 224, 3)]     0         
                                                                 
 block1_conv1 (Conv2D)       (None, 224, 224, 64)      1792      
                                                                 
 block1_conv2 (Conv2D)       (None, 224, 224, 64)      36928     
                                                                 
 block1_pool (MaxPooling2D)  (None, 112, 112, 64)      0         
                                                                 
 block2_conv1 (Conv2D)       (None, 112, 112, 128)     73856     
                                                                 
 block2_conv2 (Conv2D)       (None, 112, 112, 128)     147584    
                                                                 
 block2_pool (MaxPooling2D)  (None, 56, 56, 128)       0         
                                                                 
 block3_conv1 (Conv2D)       (None, 56, 56, 256)       295168    
                                                                 
 block3_conv2 (Conv2D)       (None, 56, 56, 256)       590080    
                                                                 
 block3_conv3 (Conv2D)       (None, 56, 56, 256)       590080    
                                                                 
 block3_pool (MaxPooling2D)  (None, 28, 28, 256)       0         
                                                                 
 block4_conv1 (Conv2D)       (None, 28, 28, 512)       1180160   
                                                                 
 block4_conv2 (Conv2D)       (None, 28, 28, 512)       2359808   
                                                                 
 block4_conv3 (Conv2D)       (None, 28, 28, 512)       2359808   
                                                                 
 block4_pool (MaxPooling2D)  (None, 14, 14, 512)       0         
                                                                 
 block5_conv1 (Conv2D)       (None, 14, 14, 512)       2359808   
                                                                 
 block5_conv2 (Conv2D)       (None, 14, 14, 512)       2359808   
                                                                 
 block5_conv3 (Conv2D)       (None, 14, 14, 512)       2359808   
                                                                 
 block5_pool (MaxPooling2D)  (None, 7, 7, 512)         0         
                                                                 
 flatten (Flatten)           (None, 25088)             0         
                                                                 
 fc1 (Dense)                 (None, 4096)              102764544 
                                                                 
 fc2 (Dense)                 (None, 4096)              16781312  
                                                                 
 predictions (Dense)         (None, 1000)              4097000   
                                                                 
=================================================================
Total params: 138,357,544
Trainable params: 138,357,544
Non-trainable params: 0
_________________________________________________________________

简简单单1亿的参数的模型。哈哈。

编译一下:

复制代码
# 编译模型  
# 设置初始学习率  
initial_learning_rate = 1e-4  
lr_schedule = tf.keras.optimizers.schedules.ExponentialDecay(  
    initial_learning_rate=initial_learning_rate,  
    decay_steps=30,  
    decay_rate=0.92,  
    staircase=True  
)  
  
# 设置优化器  
opt = tf.keras.optimizers.Adam(learning_rate=initial_learning_rate)  
  
model.compile(  
    optimizer=opt,  
    loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=False),  
    metrics=['accuracy']  
)

训练模型:

复制代码
# 训练模型  
epochs = 20  
history = model.fit(  
    train_ds,  
    validation_data=val_ds,  
    epochs=epochs,  
)

训练效果不错,可视化看看:

复制代码
acc = history.history['accuracy']
val_acc = history.history['val_accuracy']

loss = history.history['loss']
val_loss = history.history['val_loss']

epochs_range = range(epochs)

plt.figure(figsize=(12, 4))
plt.subplot(1, 2, 1)
plt.plot(epochs_range, acc, label='Training Accuracy')
plt.plot(epochs_range, val_acc, label='Validation Accuracy')
plt.legend(loc='lower right')
plt.title('Training and Validation Accuracy')

plt.subplot(1, 2, 2)
plt.plot(epochs_range, loss, label='Training Loss')
plt.plot(epochs_range, val_loss, label='Validation Loss')
plt.legend(loc='upper right')
plt.title('Training and Validation Loss')
plt.show()

果然超赞。

改成动态学习率的结果:

复制代码
opt = tf.keras.optimizers.Adam(learning_rate=lr_schedule)
5. 手动搭建VGG-16模型



VGG-16的网络 有13个卷积层(被5个max-pooling层分割)和3个全连接层(FC),所有卷积层过滤器的大小都是3X3,步长为1,进行padding。5个max-pooling层分别在第2、4、7、10,13卷积层后面。每次进行池化(max-pooling)后,特征图的长宽都缩小一半,但是channel都翻倍了,一直到512。最后三个全连接层大小分别是4096,4096, 1000,我们使用的是咖啡豆识别,根据数据集的类别数量修改最后的分类数量(即从1000改成len(class_names))

复制代码
-----------------------------
Model: "model"
_________________________________________________________________
 Layer (type)                Output Shape              Param #   
=================================================================
 input_1 (InputLayer)        [(None, 224, 224, 3)]     0         
                                                                 
 block1_conv1 (Conv2D)       (None, 224, 224, 64)      1792      
                                                                 
 block1_conv2 (Conv2D)       (None, 224, 224, 64)      36928     
                                                                 
 block1_pool (MaxPooling2D)  (None, 112, 112, 64)      0         
                                                                 
 block2_conv1 (Conv2D)       (None, 112, 112, 128)     73856     
                                                                 
 block2_conv2 (Conv2D)       (None, 112, 112, 128)     147584    
                                                                 
 block2_pool (MaxPooling2D)  (None, 56, 56, 128)       0         
                                                                 
 block3_conv1 (Conv2D)       (None, 56, 56, 256)       295168    
                                                                 
 block3_conv2 (Conv2D)       (None, 56, 56, 256)       590080    
                                                                 
 block3_conv3 (Conv2D)       (None, 56, 56, 256)       590080    
                                                                 
 block3_pool (MaxPooling2D)  (None, 28, 28, 256)       0         
                                                                 
 block4_conv1 (Conv2D)       (None, 28, 28, 512)       1180160   
                                                                 
 block4_conv2 (Conv2D)       (None, 28, 28, 512)       2359808   
                                                                 
 block4_conv3 (Conv2D)       (None, 28, 28, 512)       2359808   
                                                                 
 block4_pool (MaxPooling2D)  (None, 14, 14, 512)       0         
                                                                 
 block5_conv1 (Conv2D)       (None, 14, 14, 512)       2359808   
                                                                 
 block5_conv2 (Conv2D)       (None, 14, 14, 512)       2359808   
                                                                 
 block5_conv3 (Conv2D)       (None, 14, 14, 512)       2359808   
                                                                 
 block5_pool (MaxPooling2D)  (None, 7, 7, 512)         0         
                                                                 
 flatten (Flatten)           (None, 25088)             0         
                                                                 
 fc1 (Dense)                 (None, 4096)              102764544 
                                                                 
 fc2 (Dense)                 (None, 4096)              16781312  
                                                                 
 predictions (Dense)         (None, 4)                 16388     
                                                                 
=================================================================
Total params: 134,276,932
Trainable params: 134,276,932
Non-trainable params: 0
_________________________________________________________________
相关推荐
深蓝AI3 小时前
不调模型不改壳:CMU 开源 Hermit,给 Agent 外挂一个能训练的适配器
人工智能·agent
汤姆宝库5 小时前
世界模型深拆:视频生成、潜在模拟与物理直觉
人工智能
weixin_468466858 小时前
从“看懂”到“做到”:视觉-语言-动作模型如何让机器人真正执行指令
人工智能·ai·机器人·大语言模型·前沿科技
朋友圈自动点赞工具8 小时前
科学AI插件化:从蛋白质结构到古籍修复
人工智能
龙粤GEO9 小时前
实体Entity在GEO中代表什么含义
人工智能
剑雨巍巍10 小时前
AI Agent面试之基础概念
人工智能
微帧Visionular10 小时前
AI视频单帧清晰,播放时却闪烁,原因是什么?
人工智能·深度学习·音视频
武子康10 小时前
MultiNet6 空闲崩溃:`EXCVADDR=0x8` 后又出现 `CORRUPT HEAP`
人工智能·后端·agent
云智慧AIOps社区10 小时前
智能巡检机器人应用场景解析:机房巡检、园区安防、管廊巡视与展厅导览
人工智能·机器人·具身智能·智能巡检机器人·企业级智能巡检机器人·机房巡检机器人·导览机器人
EnCi Zheng10 小时前
Agent 如何进行工具调用:从一次 Function Calling 到生产级工具编排的完整链路
大数据·人工智能·agent·ai编程·工具调用