运动鞋识别-第五周

  • 本文为365天深度学习训练营 中的学习记录博客
  • 参考文章:Pytorch实战 | 第P5周:运动鞋识别
  • 原作者:K同学啊|接辅导、项目定制
    要求:
  1. 了解如何设置动态学习率(重点)
  2. 调整代码使测试集accuracy到达84%。

拔高(可选):

  1. 保存训练过程中的最佳模型权重
  2. 调整代码使测试集accuracy到达86%。

我的环境:

● 语言环境:Python3.8
● 编译器:Pycharm
● 深度学习环境:Pytorch 1.10
● 显卡: RTX 3060

前言:

项目整体框架和之前一样,只是数据集改成了运动鞋。

1.实验记录

1.1 显示图片信息


#%%
import matplotlib.pyplot as plt
 # 指定图片大小,图像大小为20宽、5高的绘图(单位为英寸inch)
plt.figure(figsize=(80, 20))
for i, imgs in enumerate(X[:20]):
    # 维度缩减X
    npimg = imgs.numpy().transpose((1, 2, 0))
    # 将整个figure分成2行10列,绘制第i+1个子图。
    plt.subplot(2, 10, i+1)
    plt.imshow(npimg, cmap=plt.cm.binary)
    plt.axis('off')

运动鞋识别-第五周_第1张图片

1.2 模型结构

class Model(nn.Module):
    def __init__(self):
        super(Model, self).__init__()
        self.conv1=nn.Sequential(
            nn.Conv2d(3, 12, kernel_size=5, padding=0), # 12*220*220
            nn.BatchNorm2d(12),
            nn.ReLU())

        self.conv2=nn.Sequential(
            nn.Conv2d(12, 12, kernel_size=5, padding=0), # 12*216*216
            nn.BatchNorm2d(12),
            nn.ReLU())

        self.pool3=nn.Sequential(
            nn.MaxPool2d(2))                              # 12*108*108

        self.conv4=nn.Sequential(
            nn.Conv2d(12, 24, kernel_size=5, padding=0), # 24*104*104
            nn.BatchNorm2d(24),
            nn.ReLU())

        self.conv5=nn.Sequential(
            nn.Conv2d(24, 24, kernel_size=5, padding=0), # 24*100*100
            nn.BatchNorm2d(24),
            nn.ReLU())

        self.pool6=nn.Sequential(
            nn.MaxPool2d(2))                              # 24*50*50

        self.dropout = nn.Sequential(
            nn.Dropout(0.2))

        self.fc=nn.Sequential(
            nn.Linear(24*50*50, len(classeNames)))

    def forward(self, x):

        batch_size = x.size(0)
        x = self.conv1(x)  # 卷积-BN-激活
        x = self.conv2(x)  # 卷积-BN-激活
        x = self.pool3(x)  # 池化
        x = self.conv4(x)  # 卷积-BN-激活
        x = self.conv5(x)  # 卷积-BN-激活
        x = self.pool6(x)  # 池化
        x = self.dropout(x)
        x = x.view(batch_size, -1)  # flatten 变成全连接网络需要的输入 (batch, 24*50*50) ==> (batch, -1), -1 此处自动算出的是24*50*50
        x = self.fc(x)

        return x

运动鞋识别-第五周_第2张图片

1.3 动态学习率

学习率是我们日常调参经常都会用到的参数,手动调整学习率的话费时费力。pytorch为我们封装好了动态学习率调整的方法,其方法在torch.optim.lr_scheduler库中。具体使用方法可以参考官方文档.
下面是代码示例:

>>> optimizer = torch.optim.Adam(...) #选择一种优化器
>>> scheduler = torch.optim.lr_scheduler.... # 选择一种动态调整学习率的方法,可以是下面几种之一
>>> for epoch in range(100):
>>>     train(...)
>>>     validate(...)
>>>     optimizer.step()
>>>     scheduler.step() # 需要在优化器参数更新之后再动态调整学习率

1.基于epoch数值:

LambdaLR(optimizer,lr_lambda):将每一个参数组的学习率调整为初始化学习率lr的给定函数倍, fine-tune用
StepLR(optimizer,step_size,gamma):每隔step_size个epoch就对每一参数组的学习率按gamma参数进行一次衰减,比如设置step_size=30,gamma=0.1,lr=0.5,那么
lr = 0.05 if epoch < 30
lr = 0.005 if 30 <= epoch < 60
lr = 0.0005 if 60 <= epoch < 90

ExponetialLR(optimizer,gamma):每个epoch都对当前学习率根据gamma作一个动态调整,相当于做以gamma为底,epoch为幂次的指数运算.
MultiStepLR(optimizer,milestones):当epoch的数目增加到一个里程碑(milestones)时,对学习率基于gamma做一个动态调整,其中milestones是一个关于epoch数值的list,表示在达到哪个epoch范围内开始变化

2.其他方法:**

ReduceLROnPlateau(optimizer,mode,last_epoch):基于验证指标的调整法。当指标停止改善时,降低学习率,通常将学习率降低2-10倍。mode=min,代表当度量指标停止下降时,开始减小学习率;当选择max时,代表当度量指标停止上升时,开始减小学习率。
CyclicLR(optimizer,base_lr,max_lr):根据周期性学习率策略(CLR)确定每个参数组的学习率,该策略以恒定的频率在base_lr和max_lr之间循环学习率,base_lr和max_lr之间的距离可以在每次迭代或每个周期的基础上进行缩放。

1.4 训练结果

运动鞋识别-第五周_第3张图片
运动鞋识别-第五周_第4张图片

1.5 指定图片预测

from PIL import Image

classes = list(train_dataset.class_to_idx)

def predict_one_image(image_path, model, transform, classes):

    test_img = Image.open(image_path).convert('RGB')
    # plt.imshow(test_img)  # 展示预测的图片

    test_img = transform(test_img)
    img = test_img.to(device).unsqueeze(0)

    model.eval()
    output = model(img)

    _,pred = torch.max(output,1)
    pred_class = classes[pred]
    print(f'预测结果是:{pred_class}')

    # 预测训练集中的某张照片
predict_one_image(image_path='./data/5-data/test/adidas/1.jpg',
                  model=model,
                  transform=train_transforms,
                  classes=classes)

在这里插入图片描述

2. 模型改进

2.1 改进

学习率设置为 每 10 个epoch衰减到原来的 0.98

#
lr = start_lr * (0.98** (epoch // 10)) 

使用Adam优化器

optimizer  = torch.optim.Adam(model.parameters(), lr=learn_rate)

2.2 调试结果

运动鞋识别-第五周_第5张图片
运动鞋识别-第五周_第6张图片

2.3 保存模型权重和参数

模型保存

模型的本质是一堆用某种结构存储起来的参数,保存有两种方式。一种是直接将模型整个保存下来,然后再加载模型,这样比较消耗内存。另一种则是保存模型的参数,比如weights和bias.本文采用第二种办法。

PATH = './model.pth'  # 保存的参数文件名
torch.save(model.state_dict(), PATH)
model.load_state_dict(torch.load(PATH, map_location=device))

2.4 总结

本此详细学习了动态学习率的相关知识,通常采用基于epoch数值的方法。此外,还学习了保存模型和加载模型的方法。

参考

动态学习率
模型保存

你可能感兴趣的:(深度学习,pytorch,python)