题 目: 基于ResNet残差网络优化梯度下降算法实现图像分类

目 录

引言 4
1.ResNet残差神经网络介绍 5
1.1 ResNet残差神经网络的研究现状 5
1.2 ResNet残差神经网络的原理 7
1.3 ResNet残差神经网络的实现步骤 8
1.3.1导入必要的库和模块 8
1.3.2数据预处理 8
1.3.3构建ResNet模型 8
1.3.4模型编译与训练 9
1.3.5模型评估 9
2.实验 9
2.1 海贼王人物数据集 9
2.2运行环境 10
2.3源代码 10
2.3.1 ResNet-18残差块 10
2.3.2 ResNet-18基本骨架 11
2.3.3 ResNet-18残差神经网络的训练 12
2.3.4 ResNet-18残差神经网络的预测 16
2.3.5 GUI页面的实现 18
2.4实现界面截图 19
2.4.1 预测成功截图 19
2.4.2 训练过程截图 20
2.5实验结果分析比对 21
2.5.1 ResNet-18训练批次上的对比 21
3.展望 21
4.总结 22
参考文献 23

基于ResNet残差神经网络优化梯度下降算法实现海贼王图像分类

摘 要:本研究旨在通过基于ResNet残差神经网络的方法对海贼王图像分类问题进行研究。海贼王是一个常用的图像分类基准数据集,包含5个不同类别的图像样本。为了提高分类准确度和模型的泛化能力,我们采用了ResNet作为基础网络结构。ResNet是一种深度残差神经网络,通过引入残差连接解决了深层网络训练中的梯度消失和过拟合问题。我们在海贼王数据集上训练和测试了基于ResNet的图像分类模型,并与传统的卷积神经网络进行了对比实验。实验结果表明,基于ResNet的模型在海贼王图像分类任务中具有更好的性能和鲁棒性,有效提高了分类准确度。本研究对于深度学习在图像分类领域的应用具有重要的参考价值。
关键词:ResNet,深度学习,残差神经网络,海贼王,图像分类,梯度下降算法

引言

随着计算机视觉和人工智能领域的迅速发展,图像分类成为了其中一个重要的研究方向。图像分类的任务是将输入的图像分配给预定义的类别,具有广泛的应用领域,包括目标识别、图像检索和自动驾驶等。然而,由于图像数据的复杂性和高维度特征,传统的图像分类方法在处理复杂数据集时面临着挑战。
近年来,深度学习技术的兴起为图像分类任务带来了革命性的突破。其中,卷积神经网络(Convolutional Neural Network,简称CNN)作为一种强大的模型,取得了许多重要的成果。然而,在深层网络中,随着网络层数的增加,出现了梯度消失和梯度爆炸等问题,导致网络的训练变得困难。为了解决这一问题,ResNet(Residual Neural Network)被提出。
ResNet是由Kaiming He等人于2015年提出的一种残差神经网络结构。它通过引入残差块(residual block)来构建深层网络,有效地解决了梯度消失和梯度爆炸的问题,并且在图像分类任务中取得了显著的性能提升。CIFAR-10是一个广泛用于图像分类任务的数据集,包含了5个不同类别的500张32x32像素的彩色图像。本课题旨在利用ResNet残差神经网络对haizeiwang数据集进行图像分类,进一步验证其在图像分类任务中的有效性和优越性。
本研究的目标是设计并实现一个基于ResNet残差神经网络的图像分类模型,以提高对海贼王数据集中图像的准确分类率。具体而言,本研究将通过以下步骤实现目标:
1.对海贼王数据集进行预处理,包括图像的加载、归一化和数据增强 等处理;
2.设计并搭建ResNet残差神经网络模型,包括残差块的构建和网络的层 级结构;
3.使用海贼王数据集对搭建的模型进行训练和优化;
4.对模型进行评估和性能分析,包括准确率、召回率和训练收敛速度等指标的考察。
本研究的成果有望为图像分类领域的研究和实践提供有益的参考,并为进一步探索深度学习在图像处理任务中的应用奠定基础。

1.ResNet残差神经网络介绍

1.1 ResNet残差神经网络的研究现状

在计算机视觉领域,深度神经网络已经在图像分类任务中取得了显著的成功。然而,随着网络深度的增加,传统的深度神经网络面临着梯度消失和梯度爆炸等问题,导致网络难以训练和优化。为了解决这一问题,2015年提出了ResNet(Residual Neural Network)残差神经网络。目前ResNet已经出了更深层次的网络结构,如ResNet-50、ResNet-101等,ResNet残差网络不同体系的结构图如图1所示。

图 1 ResNet残差网络结构体系
ResNet引入了残差模块,通过引入跳跃连接(shortcut connection)的方式,将输入信号直接传递到后续层,使得网络可以更容易地学习恒等映射,从而有效地解决了梯度消失的问题。ResNet的核心思想是通过残差学习来构建更深的网络,使得网络的层数可以达到几十甚至上百层,同时仍然能够保持较好的性能。
自ResNet提出以来,它在图像分类任务中表现出了卓越的性能,成为当今深度学习中最重要和广泛应用的模型之一。ResNet不仅在haizeiwang、ImageNet等公共数据集上取得了领先的结果,而且在其他计算机视觉任务中,如目标检测、语义分割等也取得了显著的进展。
此外,研究者们也对ResNet进行了不断的改进和优化。一些研究工作探索了更加高效的残差模块设计,例如使用批标准化、预激活等技术来改进网络性能。同时,研究者们还提出了各种变体的ResNet,如Wide ResNet、DenseNet等,进一步提升了网络性能。

图 2 ResNet-18与ResNet-50网络结构模型对比
总之,ResNet残差神经网络通过引入残差学习和跳跃连接的设计思想,成功解决了深度神经网络的训练问题,并在图像分类任务中取得了显著的成果。它的出现不仅推动了深度学习的发展,也为其他相关领域的研究提供了有益的启示。

1.2 ResNet残差神经网络的原理

ResNet(Residual Neural Network)残差神经网络的工作原理基于残差学习的概念。传统的深度神经网络通过堆叠多层网络来学习输入和输出之间的映射关系。然而,随着网络层数的增加,网络变得更加复杂,梯度在反向传播过程中容易消失或爆炸,导致网络难以训练。
为了解决这个问题,ResNet引入了残差模块。残差模块通过引入跳跃连接(shortcut connection)来构建网络。在传统的神经网络中,每一层都会对输入进行变换和映射,而残差模块则允许输入信号直接跳过部分层,直接传递到后续层。这样的设计使得网络可以更容易地学习恒等映射,即使添加了更多的层次。
具体来说,残差模块的工作原理是将输入信号与学习的残差函数相加,然后通过激活函数进行非线性变换。这样,残差模块实质上学习的是输入与输出之间的残差(即差异),而不是直接学习输入到输出的映射关系。通过这种方式,网络可以更加容易地优化残差,从而更好地适应训练数据的特征。

图 3 ResNet残差块
通过使用残差模块图3,ResNet可以构建非常深的网络,例如100层以上的网络。这种设计使得网络可以更好地捕捉图像中的细节和复杂特征,进而提高了图像分类的性能。此外,跳跃连接还有助于减轻梯度消失的问题,使得网络更易于训练和收敛。
总结起来,ResNet残差神经网络的工作原理是通过引入残差学习和跳跃连接的方式来构建深层网络。它允许网络直接学习输入与输出之间的残差,从而更好地适应训练数据的特征。这一设计思想不仅有效地解决了梯度消失和网络训练问题,还在图像分类等任务中取得了卓越的性能。

1.3 ResNet残差神经网络的实现步骤

在使用ResNet-18网络训练CIFAR-10数据集时,大致分为以下几个步骤:
1.配置相应的环境
2.数据预处理
3.构建ResNet模型
4.模型编译与训练
5.模型评估

1.3.1导入必要的库和模块

在Python中,你需要导入用于深度学习的库和模块,如TensorFlow或PyTorch,以及用于数据处理的库,如NumPy。

1.3.2数据预处理

a.收集CIFAR-10数据集:可以从CIFAR-10官方网站下载,在研究中使用的并不是官方提供的数据集,官方提供的数据集不利于我们平时的练习。
b. 数据加载: 加载CIFAR-10数据集并将其分为训练集和测试集。确保对图像数据进行适当的预处理,例如归一化和标准化。

1.3.3构建ResNet模型

a. 定义残差单元: 残差单元是ResNet的关键组成部分,它包含了跳跃连接(skip connection)和卷积层。你可以定义一个或多个残差单元,这取决于所使用的ResNet版本(如ResNet-18、ResNet-34等)。
b. 堆叠残差单元: 根据所选的ResNet版本,将多个残差单元堆叠在一起,以构建完整的ResNet模型。确保在每个残差单元之间使用合适的池化层或卷积层进行下采样,以适应数据集的尺寸。

图 4 ResNet-18流程图

1.3.4模型编译与训练

a. 定义损失函数和优化器: 选择适当的损失函数,如交叉熵损失,以及优化器,如随机梯度下降(SGD)或Adam。
b. 编译模型: 使用选定的损失函数和优化器来编译ResNet模型。
c. 训练模型: 使用训练集数据对ResNet模型进行训练。在每个训练周期(epoch)中,将输入数据提供给模型,并根据预测结果和真实标签计算损失,然后通过反向传播和优化器来更新模型的权重。

1.3.5模型评估

a. 使用测试集数据评估模型性能: 将测试集数据提供给已训练的ResNet模型,计算模型在测试集上的准确率或其他性能指标。
可选的进一步改进: 如果模型的性能不够理想,你可以尝试使用一些技巧来改善模型的性能,例如数据增强(data augmentation)、学习率调度(learning rate scheduling)或正则化(regularization)。

2.实验

2.1 海贼王人物数据集

图 5 海贼王人物数据集
海贼王人物数据集,是一个在网络上自己制作的数据集
海贼王人物数据集的类别如下:
路飞,乔巴,娜美,索隆,罗宾

海贼王人物数据集数据集的特点如下:
A.数据集规模较小,数据集包含500个训练图像和100个测试图像。由于规模相对较小,使用该数据集可以更快地进行模型训练和评估。
B.多样的类别:海贼王人物数据集数据集包含多个类别

2.2运行环境

系统:Windows 10 专业版
CPU :Intel® Core™ i5-8265U CPU @1.60GHz 1.80 GHz
GPU :NVIDIA GeForce MX110
内存:8.00 GB (7.88 GB 可用)
开发软件:Pycharm 2021
开发环境:Anaconda3
开发工具:Colab记事本、T4 GPU
综 合:云端训练模型权重,本地进行预测

2.3源代码

2.3.1 ResNet-18残差块

ResidualBlock类定义了一个残差块,它包含两个卷积层和批归一化层。残差块的左侧路径是卷积-批归一化-ReLU-卷积-批归一化的序列。如果 stride 不等于 1 或 inchannel 不等于 outchannel,则在残差块的右侧路径添加一个卷积层和批归一化层,用于进行维度匹配。forward 方法实现了残差块的前向传播,将输入 x 通过左侧路径的卷积层和右侧路径的卷积层得到输出,并通过 ReLU 激活函数激活后返回。
class ResidualBlock(nn.Module):
def init(self, inchannel, outchannel, stride=1):
super(ResidualBlock, self).init()
self.left = nn.Sequential(
nn.Conv2d(inchannel, outchannel, kernel_size=3, stride=stride, padding=1, bias=False),
nn.BatchNorm2d(outchannel),
nn.ReLU(inplace=True),
nn.Conv2d(outchannel, outchannel, kernel_size=3, stride=1, padding=1, bias=False),
nn.BatchNorm2d(outchannel)
)
self.shortcut = nn.Sequential()
if stride != 1 or inchannel != outchannel:
self.shortcut = nn.Sequential(
nn.Conv2d(inchannel, outchannel, kernel_size=1, stride=stride, bias=False),
nn.BatchNorm2d(outchannel)
)
def forward(self, x):
out = self.left(x)
out += self.shortcut(x)
out = F.relu(out)
return out

2.3.2 ResNet-18基本骨架

ResNet 类定义了整个 ResNet 模型的结构。在初始化方法 init 中,首先定义了初始通道数 self.inchannel 和第一个卷积层 self.conv1,包含一个卷积层、批归一化层和 ReLU 激活函数。接下来通过调用 make_layer 方法构建了四个不同的残差层 self.layer1、self.layer2、self.layer3 和 self.layer4。每个残差层包含了多个残差块,并通过 make_layer 方法传入残差块类型、通道数、残差块数量和步长来创建。最后,定义了全连接层 self.fc,用于进行分类预测。
class ResNet(nn.Module):
def init(self, ResidualBlock, num_classes=10):
super(ResNet, self).init()
self.inchannel = 64
self.conv1 = nn.Sequential(
nn.Conv2d(3, 64, kernel_size=3, stride=1, padding=1, bias=False),
nn.BatchNorm2d(64),
nn.ReLU(),
)
self.layer1 = self.make_layer(ResidualBlock, 64, 2, stride=1)
self.layer2 = self.make_layer(ResidualBlock, 128, 2, stride=2)
self.layer3 = self.make_layer(ResidualBlock, 256, 2, stride=2)
self.layer4 = self.make_layer(ResidualBlock, 512, 2, stride=2)
self.fc = nn.Linear(512, num_classes)

def make_layer(self, block, channels, num_blocks, stride):
    strides = [stride] + [1] * (num_blocks - 1)   #strides=[1,1]
    layers = []
    for stride in strides:
        layers.append(block(self.inchannel, channels, stride))
        self.inchannel = channels
    return nn.Sequential(*layers)

def forward(self, x):
    out = self.conv1(x)
    out = self.layer1(out)
    out = self.layer2(out)
    out = self.layer3(out)
    out = self.layer4(out)
    out = F.avg_pool2d(out, 4)
    out = out.view(out.size(0), -1)
    out = self.fc(out)
    return out

def ResNet18():

return ResNet(ResidualBlock)

2.3.3 ResNet-18残差神经网络的训练

首先导入了需要的PyTorch模块和库。设置是否使用GPU进行训练,通过检查是否有可用的CUDA设备。定义了超参数,包括训练的总轮次(EPOCH)、批处理大小(BATCH_SIZE)、学习率(LR)等。
然后使用torchvision.transforms模块定义了数据预处理的操作,包括随机裁剪、随机水平翻转和归一化等。使用torchvision.datasets.ImageFolder创建了训练集和测试集,并使用torch.utils.data.DataLoader将数据集包装成可迭代的数据加载器。
定义了模型对象resnet18,使用自定义的ResNet18类创建ResNet-18模型,并将其移动到GPU上。
定义了损失函数loss_fn,采用交叉熵损失函数。
定义了优化器optimizer,采用SGD优化器进行参数优化。
使用torch.utils.tensorboard.SummaryWriter创建了一个TensorBoard的可视化写入器。开始训练的主循环,遍历每个epoch。将模型设置为训练模式(resnet18.train())。
对每个batch进行训练:准备数据并将其移动到GPU上。将梯度清零、前向传播、计算预测输出和损失、反向传播、更新模型参数、计算训练集的累计损失、准确率和样本总数,并记录到TensorBoard中。
每个epoch结束后,在测试集上进行模型评估:将模型设置为评估模式(resnet18.eval())。对每个batch进行测试,并计算测试集的累计损失、准确率和样本总数。将测试集的损失和准确率记录到TensorBoard中。如果当前epoch的准确率超过之前记录的最佳准确率,保存模型参数。训练结束后,输出训练完成的提示信息。
超参数设置
EPOCH = 20 # 遍历数据集次数
pre_epoch = 0 # 定义已经遍历数据集的次数
BATCH_SIZE=4
LR = 0.001 # 学习率

print(“开始加载CIFAR10数据集!”)
准备数据集并预处理
准备数据集并预处理
transform_train = transforms.Compose([
transforms.Resize([32,32]),
transforms.RandomCrop(32, padding=4), # 先四周填充0,在吧图像随机裁剪成32*32
transforms.RandomHorizontalFlip(), # 图像一半的概率翻转,一半的概率不翻转
transforms.ToTensor(),
transforms.Normalize((0.4914, 0.4822, 0.4465), (0.2023, 0.1994, 0.2010)), # R,G,B每层的归一化用到的均值和方差
])

transform_test = transforms.Compose([
transforms.Resize([32, 32]),
transforms.ToTensor(),
transforms.Normalize((0.4914, 0.4822, 0.4465), (0.2023, 0.1994, 0.2010)),
])

trainset = torchvision.datasets.ImageFolder(root=‘data/train’, transform=transform_train) # 训练数据集
train_loader = torch.utils.data.DataLoader(trainset, batch_size=BATCH_SIZE, shuffle=True,
num_workers=2) # 生成一个个batch进行批训练,组成batch的时候顺序打乱取

testset = torchvision.datasets.ImageFolder(root=‘data/test’, transform=transform_test)
validate_loader = torch.utils.data.DataLoader(testset, batch_size=100, shuffle=True, num_workers=2)

classes = (‘lufei’, ‘luobin’, ‘namei’, ‘qiaoba’, ‘suoluo’)
print(“CIFAR10数据集加载完毕!”)
print(“开始ResNet网络模型初始化!”)模型定义-ResNet
resnet18 = ResNet18().to(device)

定义损失函数和优化方式
loss_fn = nn.CrossEntropyLoss() # 损失函数为交叉熵,多用于多分类问题
loss_fn=loss_fn.to(device)
optimizer = optim.SGD(resnet18.parameters(), lr=LR, momentum=0.9,
weight_decay=5e-4) # 优化方式为mini-batch momentum-SGD,并采用L2正则化(权重衰减)

#记录训练的次数
total_train_step = 0
#记录测试的次数
total_test_step = 0

添加tensorboard画图可视化
writer = SummaryWriter(“logs_train”)

print(“ResNet网络模型初始化完毕!”)
训练
if name == “main”:
best_acc = 85 # 2 初始化best test accuracy
best_epoch=0
# 有需要可以打开,接着上次训练好的权重训练
#print(“加载模型…”)
#with open(“pth/resnet18_12.pth”,‘rb’) as f:
#resnet18.load_state_dict(torch.load(f))
#print(“加载完毕!”)
print(“开始训练! Resnet-18! 冲!”) # 定义遍历数据集的次数
for epoch in range(pre_epoch, EPOCH):
print(f’--------第{epoch + 1}轮训练开始---------')
resnet18.train()
total_train_loss = 0.0
correct = 0.0
total = 0.0
for data in train_loader:
# print(“-------”,i)
# 准备数据
inputs, labels = data
inputs, labels = inputs.to(device), labels.to(device)
optimizer.zero_grad()

        # forward + backward
        outputs = resnet18(inputs)
        loss = loss_fn(outputs, labels)
        loss.backward()
        optimizer.step()

        # 每训练100个batch打印一次loss和准确率
        total_train_loss += loss.item()
        _, predicted = torch.max(outputs.data, 1)
        total += labels.size(0)
        total_train_step+=1
        correct += predicted.eq(labels.data).cpu().sum()
        if total_train_step % 10 == 0: print('[训练次数:%d] Loss: %.03f' % (total_train_step, total_train_loss))
        writer.add_scalar("train_loss", loss.item(), total_train_step)

    # 每训练完一个epoch测试一下准确率
    print("开始测试!")
    with torch.no_grad():
        correct = 0
        total = 0
        total_test_loss=0
        for data in validate_loader:
            resnet18.eval()
            images, labels = data
            images, labels = images.to(device), labels.to(device)
            outputs = resnet18(images)
            loss = loss_fn(outputs, labels)
            total_test_loss+=loss.item()
            # 取得分最高的那个类 (outputs.data的索引号)
            _, predicted = torch.max(outputs.data, 1)
            total += labels.size(0)
            correct += (predicted == labels).sum().item()
            # result = torch.floor_divide(correct, total)
        # print('测试分类准确率为:%.3f%%' % (100 * result))
        acc = 100 * correct / total
        print(f"测试集上的loss:{total_test_loss}")
        print(f'测试分类准确率为:{acc}')
        # 将每次测试结果实时写入acc.txt文件中
        print('Saving model......')
        torch.save(resnet18.state_dict(), f'pth/resnet18_{epoch + 1}.pth')
        writer.add_scalar("test_loss", total_test_loss, total_test_step)
        total_test_step = total_test_step + 1
        # 记录最佳测试分类准确率并写入best_acc.txt文件中
        if acc > best_acc:
            f3 = open("best_acc.txt", "w")
            f3.write(f"训练轮次为{epoch + 1}时,准确率最高!准确率为{acc}")
            f3.close()
            best_acc = acc
print("训练结束!")

2.3.4 ResNet-18残差神经网络的预测

首先,定义了一个 data_transform 变量,它是一个 transforms.Compose 对象,用于对输入图像进行预处理操作,包括将图像转换为张量、归一化和调整大小为 32x32 像素。如果输入的图像模式不是 RGB,则使用 convert 方法将其转换为 RGB 模式。使用定义的 data_transform 对象对图像进行预处理,得到处理后的图像。使用 torch.unsqueeze 函数在张量上增加一个维度,将其形状从 (3, 32, 32) 变为 (1, 3, 32, 32)。这是因为模型接受的输入是一个批次的图像,即需要在第一维添加一个批次维度。创建一个 ResNet18 模型的实例,并加载预训练的模型权重文件 ‘pth/resnet18_121.pth’。将模型设置为评估模式,通过调用 model.eval()。定义一个字典 classes,其中包含了模型的类别标签,用于将预测的类别索引映射为类别名称。使用 torch.no_grad() 上下文管理器禁用梯度计算。使用模型对处理后的图像进行预测,通过调用 model(img) 得到输出。使用 torch.squeeze 函数从输出中移除维度为 1 的维度,得到一维的输出张量。使用 torch.softmax 对输出进行 softmax 操作,得到各个类别的预测概率。使用 torch.argmax 找到预测概率最大的类别索引。将预测的类别索引转换为字符串,并使用字典 classes 找到对应的类别名称。返回预测的类别名称和对应的置信度。

data_transform = transforms.Compose([
    transforms.ToTensor(),
    transforms.Normalize((0.4914, 0.4822, 0.4465), (0.2023, 0.1994, 0.2010)),
    transforms.Resize((32,32))
])
if img.mode != "RGB":
    img = img.convert("RGB")
img = data_transform(img)
img = torch.unsqueeze(img, dim=0)

model = ResNet18()
model_weight_pth = 'pth/resnet18_20.pth'
model.load_state_dict(torch.load(model_weight_pth,map_location="cpu"))

model.eval()
classes = {'0': '路飞', '1': '罗宾', '2': '娜美', '3': '乔巴', '4': '索罗'}
with torch.no_grad():
    output = torch.squeeze(model(img))
    print(output)
    predict = torch.softmax(output, dim=0)

    predict_cla = torch.argmax(predict).numpy()

return classes[str(predict_cla)], predict[predict_cla].item()

basepath=os.path.split(os.path.split(os.getcwd())[0])[0]

2.3.5 GUI页面的实现

下面进行了GUI界面的设计,通过这个GUI我们可以轻松实现选择图片,预测图片,由于GUI页面并不作为我们介绍的重点,所以这里直接给出源代码。
class Ui_example(QWidget):
def init(self):
super().init()
self.layout = QGridLayout(self)
self.label_image = QLabel(self)
self.label_predict_result = QLabel(‘识别结果’,self)
self.label_predict_result_display = QLabel(self)
self.label_predict_acc = QLabel(‘识别准确率’,self)
self.label_predict_acc_display = QLabel(self)

    self.button_search_image = QPushButton('选择图片',self)
    self.button_run = QPushButton('运行',self)
    self.setLayout(self.layout)
    self.initUi()
def initUi(self):
    self.layout.addWidget(self.label_image,1,1,3,2)
    self.layout.addWidget(self.button_search_image,1,3,1,2)
    self.layout.addWidget(self.button_run,3,3,1,2)
    self.layout.addWidget(self.label_predict_result,4,3,1,1)
 self.layout.addWidget(self.label_predict_result_display,4,4,1,1)
    self.layout.addWidget(self.label_predict_acc,5,3,1,1)
    self.layout.addWidget(self.label_predict_acc_display,5,4,1,1)
    self.button_search_image.clicked.connect(self.openimage)
    self.button_run.clicked.connect(self.run)
    self.setGeometry(300,300,300,300)
    self.setWindowTitle('CLFAR-10十分类')
    self.show()
def openimage(self):
    global fname
    imgName, imgType = QFileDialog.getOpenFileName(self, "选择图片", "", "*.jpg;;*.png;;All Files(*)")
    jpg = QPixmap(imgName).scaled(self.label_image.width(), self.label_image.height())
    self.label_image.setPixmap(jpg)
    fname = imgName
def run(self):
    global fname
    file_name = str(fname)
    img = Image.open(file_name)
    a, b = predict_(img)
    self.label_predict_result_display.setText(a)
    self.label_predict_acc_display.setText(str(b))

2.4实现界面截图

2.4.1 预测成功截图

从图7、图8、图9中可以看到样本的预测准确率均达到了99以上

图 6 实验效果-路飞

图 7 实验效果-索罗

2.4.2 训练过程截图

图 10 测试集损失与训练集损失

2.5实验结果分析比对

2.5.1 ResNet-18训练批次上的对比

随着迭代次数的增加,损失通常会逐渐减小。这是由于模型通过反向传播和优化算法(如随机梯度下降)对权重进行调整,以最小化损失函数。在本次实验中大致可分为以下三个阶段。初始阶段:在训练开始时,损失可能较高,因为模型的权重是随机初始化的,并且尚未对数据进行有效的拟合。损失可能波动较大,但整体趋势是逐渐下降的。收敛阶段:随着训练的进行,模型逐渐学习到数据的特征和模式,损失会逐渐减小并趋于稳定。这是模型逐渐收敛到最优解的过程。过拟合阶段:如果训练迭代次数过多,模型可能会过度拟合训练数据,导致训练损失持续减小,但测试数据上的性能下降。此时,损失在训练集上继续减小,但在测试集上开始增加。

3.展望

如果要改进基于 ResNet 残差神经网络的 CIFAR-10 图像分类系统,可以考虑以下几个方面的改进:
A.模型深度:尝试使用更深的 ResNet 模型,如 ResNet-34、ResNet-50 等。增加模型的深度可以提高其表达能力,进一步提升分类性能。但要注意避免过拟合问题,可能需要增加正则化方法或使用其他优化技巧。
B.数据增强:在数据预处理阶段增加更多的数据增强操作,如旋转、缩放、平移等。通过增加数据的多样性,可以提升模型的泛化能力,并减轻过拟合的风险。
C.学习率调度:尝试使用学习率调度策略,如学习率衰减、动态调整学习率等。这可以帮助模型更好地收敛并避免陷入局部最优点。可以使用学习率调度器或自定义的学习率衰减函数。
D.结果分析和调试:对训练过程中的损失、准确率等指标进行详细分析,找出模型存在的问题和改进的空间。通过调试和分析结果,不断优化模型架构和训练策略。
这些改进方法可以根据具体情况选择和组合使用。重点是不断尝试和实验,并根据实验结果进行调整和优化,以提升基于 ResNet 残差神经网络的 CIFAR-10 图像分类系统的性能。

4.总结

本项目使用基于 ResNet 残差神经网络的方法对 海贼王 数据集进行图像分类。ResNet 是一种深度残差网络结构,通过引入残差连接(shortcut connections)解决了深层网络训练中的梯度消失和模型退化问题。
在实验中,首先对 海贼王 数据集进行预处理,包括随机裁剪、随机水平翻转和归一化操作,以提高模型的鲁棒性和泛化能力。然后,使用 ResNet18 模型作为分类器,并将其参数移动到可用的计算设备上(GPU 或 CPU)。
训练过程中,使用交叉熵损失函数作为多分类任务的损失函数,并采用随机梯度下降优化算法对模型参数进行优化。每个训练轮次中,通过批量训练对训练数据进行模型更新,使用前向传播计算预测结果,计算损失并进行反向传播更新梯度。通过记录训练过程中的训练损失和准确率,可以监控模型的训练进展。
在测试阶段,将模型切换为评估模式,禁用梯度计算,以加快推理过程。使用测试数据集进行推理,并计算损失和准确率。同时,保存准确率最高的模型权重,并将训练和测试的损失值写入 TensorBoard 中进行可视化。
通过实验结果分析,可以得出以下结论:基于 ResNet 残差神经网络的方法在 海贼王数据集上取得了较高的分类准确率。ResNet 的残差连接有助于减轻深层网络训练中的梯度消失问题,提高了模型的学习能力和性能。使用合适的超参数设置和数据增强技术可以进一步提升模型的性能。同时,通过可视化训练和测试过程中的损失值,可以直观地观察模型的收敛情况和泛化能力。
总而言之,基于 ResNet 的残差神经网络在海贼王图像分类任务中展现了强大的表现力和性能。这种网络结构和训练方法为解决深层网络训练中的问题提供了一种有效的解决方案,对于其他图像分类任务和深度学习任务也具有广泛的应用前景。

参考文献

[1]张璐瑶,王新安. 基于ResNet的CIFAR-10图像分类算法研究[J]. 深圳大学学报(理工版),2018,35(1):14-20.
[2]李岩,宋乐平. 基于ResNet的CIFAR-10图像分类算法研究[J]. 计算机应用与软件,2019,36(4):128-131.

源码资源地址

https://download.csdn.net/download/m0_73337964/90957065

Logo

脑启社区是一个专注类脑智能领域的开发者社区。欢迎加入社区,共建类脑智能生态。社区为开发者提供了丰富的开源类脑工具软件、类脑算法模型及数据集、类脑知识库、类脑技术培训课程以及类脑应用案例等资源。

更多推荐