pytorch——猫狗识别

猫狗识别

  • 训练模型
    • 导入需要的包
    • 数据加载
    • 数据预处理
    • 加载数据集并返回对应的图像和标签
    • 提取标签信息
    • 创建训练和测试的数据加载器
    • 图像分类
      • CNN的卷积神经网络模型
      • MYVGG的卷积神经网络模型
      • AlexNet的卷积神经网络模型
    • 训练过程
    • 测试过程
    • 定义了一个主函数
  • 测试模型
    • 导入需要的库
    • 加载之前训练好的模型
    • 加载新的测试图片并进行预处理
    • 对图片进行预处理
    • 对新图片进行预处理转换,并添加一个batch维度
    • 使用训练好的模型进行推理
    • 显示新的测试图片
    • 运行结果:

训练模型

导入需要的包

import torch:导入PyTorch深度学习框架。 from torch import optim:从torch模块中导入optim优化器,用于模型的优化。 import torch.nn as nn:导入torch.nn模块,其中包含了神经网络的相关函数和类。 from torch.autograd import Variable:从torch.autograd模块导入Variable类,用于封装张量并支持自动求导。 from torchvision import transforms:从torchvision模块导入transforms,用于数据的预处理和增强。
from torch.utils.data import Dataset, DataLoader:从torch.utils.data模块导入Dataset和DataLoader类,用于自定义数据集和数据加载。
from PIL import Image:从PIL库中导入Image模块,用于处理图像数据。 import torch.nn.functional as F:导入torch.nn.functional模块并给其命名为F,其中包含了一些常用的函数,如激活函数、损失函数等。

import torch
from torch import optim
import torch.nn as nn
from torch.autograd import Variable
from torchvision import transforms
from torch.utils.data import Dataset, DataLoader
from PIL import Image
import torch.nn.functional as F

数据加载

接收一个路径 path,使用PIL库中的 Image.open 方法打开指定路径的图像文件,然后通过
convert('RGB') 方法将图像转换为RGB格式。最后将转换后的图像返回。

def Myloader(path):
return Image.open(path).convert('RGB')

数据预处理

得到一个包含路径与标签的列表 该函数用于初始化数据并生成包含路径和标签的列表。函数会调用 find_label(path) 函数来获取路径
path 对应的标签。然后通过循环从 lens[0] 到 lens[1],依次生成包含路径和标签的列表项,将其添加到 data 列表中。

def init_process(path, lens):data = []name = find_label(path)for i in range(lens[0], lens[1]):data.append([path % i, name])return data

加载数据集并返回对应的图像和标签

init 方法:类的初始化方法,接收三个参数 data、transform、loader,分别表示数据集、数据转换操作、数据加载器。在初始化过程中,将这三个参数保存在类的成员变量中。

getitem 方法:用于获取数据集中指定索引 item 的数据。首先从 self.data 中根据索引 item 获取图像路径 img 和标签 label。然后通过 self.loader 加载图像,并通过 self.transform
进行图像的转换操作。最后返回经过加载和转换后的图像 img 和对应的标签 label。

len 方法:返回数据集的长度,即数据集中样本的数量。

class MyDataset(Dataset):def __init__(self, data, transform, loder):self.data = dataself.transform = transformself.loader = loderdef __getitem__(self, item):img, label = self.data[item]img = self.loader(img)img = self.transform(img)return img, labeldef __len__(self):return len(self.data)

提取标签信息

函数首先定义了两个变量first和last,分别用于记录标签字符串的起始位置和结束位置,并初始化为0。
然后通过循环遍历给定的路径字符串str,从末尾向前查找符号’%‘和’.‘,以及字符’c’或’d’和’/‘进行位置的提取。
最后根据提取的起始和结束位置,截取标签字符串name。 如果截取的标签字符串为’dog’,则返回标签值1;否则返回标签值0。

def find_label(str):first, last = 0, 0for i in range(len(str) - 1, -1, -1):if str[i] == '%' and str[i - 1] == '.':last = i - 1if (str[i] == 'c' or str[i] == 'd') and str[i - 1] == '/':first = ibreakname = str[first:last]if name == 'dog':return 1else:return 0

创建训练和测试的数据加载器

首先创建了一个图像转换操作transform,包括随机水平翻转、随机垂直翻转、调整大小为(256, 256)、转换为张量以及标准化的操作。

然后定义了四个路径变量path1、path2、path3、path4,分别表示训练集中猫的图像路径模板、训练集中狗的图像路径模板、测试集中猫的图像路径模板、测试集中狗的图像路径模板。

对每个路径使用init_process函数初始化数据,数据范围为[0, 500]和[1000,
1200],并将数据存储在相应的data1、data2、data3、data4列表中。

组合一部分训练数据和标签数据,创建训练数据集train实例,剩余数据用于测试数据集test实例。
使用DataLoader类分别创建训练数据加载器train_data和测试数据加载器test_data,设置批量大小、是否打乱数据和工作进程数。

最后返回训练数据加载器train_data和测试数据加载器test_data。

def load_data():transform = transforms.Compose([transforms.RandomHorizontalFlip(p=0.3),transforms.RandomVerticalFlip(p=0.3),transforms.Resize((256, 256)),transforms.ToTensor(),transforms.Normalize(mean=(0.5, 0.5, 0.5), std=(0.5, 0.5, 0.5))])path1 = 'D:/probject/pythonProject1/pytorch/data/training_data/cats/cat.%d.jpg'data1 = init_process(path1, [0, 500])path2 = 'D:/probject/pythonProject1/pytorch/data/training_data/dogs/dog.%d.jpg'data2 = init_process(path2, [0, 500])path3 = 'D:/probject/pythonProject1/pytorch/data/testing_data/cats/cat.%d.jpg'data3 = init_process(path3, [1000, 1200])path4 = 'D:/probject/pythonProject1/pytorch/data/testing_data/dogs/dog.%d.jpg'data4 = init_process(path4, [1000, 1200])# 1300个训练train_data = data1 + data2 + data3[0: 150] + data4[0: 150]train = MyDataset(train_data, transform=transform, loder=Myloader)# 100个测试test_data = data3[150: 200] + data4[150: 200]test = MyDataset(test_data, transform=transform, loder=Myloader)train_data = DataLoader(dataset=train, batch_size=10, shuffle=True, num_workers=0)test_data = DataLoader(dataset=test, batch_size=1, shuffle=True, num_workers=0)return train_data, test_data

图像分类

CNN的卷积神经网络模型

这段代码定义了一个名为CNN的卷积神经网络模型,用于图像分类任务,并定义了其前向传播方法forward。
在__init__方法中,定义了卷积层conv1和conv2,池化层pool,以及全连接层output和dp1(Dropout层)。

在forward方法中,对输入数据x进行前向传播计算,首先通过第一个卷积层conv1和池化层进行特征提取和下采样,然后经过第二个卷积层conv2和池化层继续提取特征和下采样。

接着将特征张量展平为一维向量,通过dp1(Dropout)进行正则化处理,最后通过全连接层output生成最终输出,其中output的输出维度是二分类(2个类别)。

# 三种网络择优选择其中一种即可
class CNN(nn.Module):def __init__(self, num_classes=2):super(CNN, self).__init__()self.conv1 = nn.Conv2d(3, 16, 3, padding=1) self.pool = nn.MaxPool2d(2, 2)self.conv2 = nn.Conv2d(16, 16, 3, padding=1)self.pool = nn.MaxPool2d(2, 2)self.output = nn.Linear(16 * 64 * 64, 2)  self.dp1 = nn.Dropout(p=0.5)def forward(self, x):x = self.pool(F.relu(self.conv1(x)))x = self.pool(F.relu(self.conv2(x)))temp = x.view(x.size()[0], -1)x = self.dp1(x)output = self.output(temp)return output, x

这段代码是一个定义了名为MYVGG的卷积神经网络模型,类似于VGG网络结构,用于图像分类任务。在该模型中,包括8个卷积层和池化层的组合,最后连接一个全连接层和Dropout层。

__init__方法中初始化了模型的网络层。每个卷积层后面跟着一个最大池化层。卷积核数量和大小逐渐增加,通过池化层逐步减小特征图的尺寸。

最后一个卷积层的输出经过展平操作后,经过一个Dropout层进行正则化处理。

输出通过全连接层output生成最终的分类结果。

forward方法定义了模型的前向传播过程。输入数据经过一系列的卷积、激活函数ReLU和池化操作,最终通过全连接层和Dropout层得到输出。

MYVGG的卷积神经网络模型

class MYVGG(nn.Module):def __init__(self, num_classes=2):super(MYVGG, self).__init__()self.conv1 = nn.Conv2d(3, 64, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv2 = nn.Conv2d(64, 64, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv3 = nn.Conv2d(64, 128, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv4 = nn.Conv2d(128, 128, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv5 = nn.Conv2d(128, 256, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv6 = nn.Conv2d(256, 256, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv7 = nn.Conv2d(256, 512, 3,padding=1)self.pool = nn.MaxPool2d(2, 2)self.conv8 = nn.Conv2d(512, 512, 3, padding=1)self.pool = nn.MaxPool2d(2, 2)self.output = nn.Linear(512, num_classes)self.dp1 = nn.Dropout(p=0.5)def forward(self, x):x = self.pool(F.relu(self.conv1(x)))x = self.pool(F.relu(self.conv2(x)))x = self.pool(F.relu(self.conv3(x)))x = self.pool(F.relu(self.conv4(x)))x = self.pool(F.relu(self.conv5(x)))x = self.pool(F.relu(self.conv6(x)))x = self.pool(F.relu(self.conv7(x)))x = self.pool(F.relu(self.conv8(x)))temp = x.view(x.size()[0], -1)x = self.dp1(x)output = self.output(temp)return output, x

AlexNet的卷积神经网络模型

AlexNet的卷积神经网络模型,类似于AlexNet网络结构,用于图像分类任务。在该模型中,包括5个卷积层和池化层的组合,最后连接一个全连接层和Dropout层。

__init__方法中初始化了模型的网络层。每个卷积层后面跟着一个最大池化层。卷积核数量和大小逐渐增加,通过池化层逐步减小特征图的尺寸。

最后一个卷积层的输出经过展平操作后,经过一个Dropout层进行正则化处理。

输出通过全连接层output生成最终的分类结果。

forward方法定义了模型的前向传播过程。输入数据经过一系列的卷积、激活函数ReLU和池化操作,最终通过全连接层和Dropout层得到输出。

class AlexNet(nn.Module):def __init__(self):super(AlexNet,self).__init__()self.conv1 = nn.Conv2d(3, 32, 3)self.pool = nn.MaxPool2d(2, 2)self.conv2 = nn.Conv2d(32, 64, 3)self.pool = nn.MaxPool2d(2, 2)self.conv3 = nn.Conv2d(64, 128, 3)self.pool = nn.MaxPool2d(2, 2)self.conv4 = nn.Conv2d(128, 256, 3)self.pool = nn.MaxPool2d(2, 2)self.conv5 = nn.Conv2d(256, 512, 3)self.pool = nn.MaxPool2d(2, 2)self.output = nn.Linear(in_features=512 * 6 * 6,out_features=2)self.dp1 = nn.Dropout(p=0.5)def forward(self,x):x = self.pool(F.relu(self.conv1(x)))x = self.pool(F.relu(self.conv2(x)))x = self.pool(F.relu(self.conv3(x)))x = self.pool(F.relu(self.conv4(x)))x = self.pool(F.relu(self.conv5(x)))temp = x.view(x.shape[0], -1)x = self.dp1(x)output = self.output(temp)return output, x

训练过程

代码实现了一个简单的训练过程,包括数据加载、模型定义、优化器设置、损失函数定义、循环训练和参数保存等步骤。 train_loader, test_loader = load_data():加载训练和测试数据集。 device = torch.device('cuda' if torch.cuda.is_available() else 'cpu'):检测是否有可用的GPU,将模型放到对应的设备上。
model = AlexNet().to(device):实例化AlexNet模型并将其移动到指定的设备上。 optimizer = optim.Adam(model.parameters(), lr=0.00004):定义Adam优化器,并传入模型参数和学习率。
criterion = nn.CrossEntropyLoss().to(device):定义交叉熵损失函数,用于计算预测值和目标值之间的损失。

训练循环中,遍历每个epoch和每个batch: optimizer.zero_grad():梯度清零。 output = model(data)[0]:通过模型进行前向传播。 loss = criterion(output, target):计算损失值。
loss.backward():反向传播计算梯度。 optimizer.step():更新模型参数。 打印每个迭代的训练损失信息。
通过torch.save()函数,模型在训练完成后会保存在指定路径下。

def train():train_loader, test_loader = load_data()epoch_num = 20# GPU计算device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')model = AlexNet().to(device)optimizer = optim.Adam(model.parameters(), lr=0.00004)criterion = nn.CrossEntropyLoss().to(device)for epoch in range(epoch_num):for batch_idx, (data, target) in enumerate(train_loader, 0):data, target = Variable(data).to(device), Variable(target.long()).to(device)optimizer.zero_grad()  # 梯度清0output = model(data)[0]  # 前向传播loss = criterion(output, target)  # 计算误差loss.backward()  # 反向传播optimizer.step()  # 更新参数if batch_idx % 10 == 0:print('Epoch: {} [{}/{} ({:.0f}%)]\tLoss: {:.6f}'.format(epoch, batch_idx * len(data), len(train_loader.dataset),100. * batch_idx / len(train_loader), loss.item()))torch.save(model, 'D:/probject/pythonProject1/pytorch/cnn.pkl')

测试过程

用于评估训练好的模型在测试集上的准确率 test()函数首先加载训练和测试数据集,并检测可用的设备(GPU或CPU)。
model =torch.load('D:/probject/pythonProject1/pytorch/cnn.pkl'):加载之前训练好的模型。

在测试循环中,遍历测试集中的每个数据样本: 将图像数据和标签移动到指定的设备上。 通过加载的模型进行前向传播,得到预测输出。
通过torch.max(outputs.data, 1)[1].data获取预测的类别。
统计总样本数total和预测正确的样本数current。

最后,计算模型在测试集上的准确率,并打印输出。准确率的计算方式是正确预测的样本数除以总样本数,然后乘以100以得到百分比表示。

def test():train_loader, test_loader = load_data()device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')model = torch.load('D:/probject/pythonProject1/pytorch/cnn.pkl')  # load modeltotal = 0current = 0for data in test_loader:images, labels = dataimages, labels = images.to(device), labels.to(device)outputs = model(images)[0]predicted = torch.max(outputs.data, 1)[1].datatotal += labels.size(0)current += (predicted == labels).sum()print('Accuracy: %d %%' % (100 * current / total))

定义了一个主函数

用于执行训练和测试过程 train()和test()函数是前面解释过的训练和测试过程,分别进行模型训练和测试。
if __name__ == '__main__'::判断是否是主程序入口,即在作为主程序运行时执行以下代码。
train():首先执行训练过程。
test():之后执行测试过程,评估训练好的模型在测试集上的准确率。

if __name__ == '__main__':train()
test()

运行结果:
在这里插入图片描述

测试模型

导入需要的库

torch:PyTorch深度学习框架。 transforms:用于图像预处理的模块。 Image:用于处理图像的PIL库。
torch.nn.functional as F:包含了各种神经网络的函数接口。
matplotlib.pyplot as plt:用于可视化的库。

import torch
from torchvision import transforms
from PIL import Image
import torch.nn.functional as F
import matplotlib.pyplot as plt

加载之前训练好的模型

# 加载模型
model = torch.load('D:/probject/pythonProject1/pytorch/cnn.pkl')

加载新的测试图片并进行预处理

# 加载新图片
new_image_path = 'noise.jpg'  # 请替换为新图片的路径
img = Image.open(new_image_path).convert('RGB')

对图片进行预处理

transforms.Compose()定义了一系列的图像预处理操作,包括调整大小、转换为张量、归一化等。

transform = transforms.Compose([transforms.Resize((256, 256)),transforms.ToTensor(),transforms.Normalize(mean=(0.5, 0.5, 0.5), std=(0.5, 0.5, 0.5))
])

对新图片进行预处理转换,并添加一个batch维度

img = transform(img)
img = img.unsqueeze(0)  # 添加batch维度

使用训练好的模型进行推理

output, _ = model(img):使用模型进行前向传播,并获取输出结果。
通过torch.max(output, 1)[1].item()获取预测类别。

output, _ = model(img)
predicted_class = torch.max(output, 1)[1].item()

展示分类结果和图片

class_names = ['cat', 'dog']
print("Predicted class:", class_names[predicted_class])

显示新的测试图片

plt.imshow(img.squeeze().numpy().transpose((1, 2, 0)))
plt.show()

运行结果:

在这里插入图片描述

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

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

相关文章

无线模块应用晶振SG5032VAN

随着物联网(IoT)和无线通信技术的迅速发展,无线模块已经成为各种智能设备的重要组成部分。在无线模块中,选择高性能的时钟源对于确保系统的稳定性和可靠性至关重要。爱普生SG5032VAN是一款LVDS差分晶振,作为一款高性能…

WINUI——Behavior(行为)小结

前言 在使用MVVM进行WINUI或WPF开发时,Command在某些时候并不能满足逻辑与UI分离的要求。这时肯定就需要其它技术的支持,Behavior就是一种。在WPF中是有Behavior直接支持的,转到WINUI后,相对有一些麻烦,于是在此记录之…

Enscape 4.1.0 软件安装教程+离线资源库

软件介绍 Enscape 是专门为建筑、规划、景观及室内设计师打造的渲染产品,无需导入导出文件,在常用的软件内部即可看到逼真的渲染效果。 你无需了解记忆各种参数的用法,一切都是傻瓜式的一键渲染,你可以把精力更多地投入到设计中…

ElementUI之el-tooltip显示多行内容

ElementUI之el-tooltip显示多行内容 文章目录 ElementUI之el-tooltip显示多行内容1. 多行文本实现2. 实现代码3. 展示效果 1. 多行文本实现 展示多行文本或者是设置文本内容的格式,使用具名 slot 分发content,替代tooltip中的content属性。 2. 实现代码 …

Sui主网升级至V1.26.2版本

Sui主网现已升级至V1.26.2版本,同时Sui协议升级至48版本。 其他升级要点如下所示: 协议 #17881 Sui原生随机性功能现在已在测试网启用。 索引器 #17649 JSON-RPC:现在JSON-RPC在查询时将返回正确的币种元数据和总供应量信息。 索引器…

【图像处理与机器视觉】灰度变化与空间滤波

基础 空间域与变换域 空间域:认为是图像本身,对于空间域的操作就是对图像中的像素直接进行修改 变换域:变换系数处理,不直接对于图像的像素进行处理 邻域 图像中某点的邻域被认为是包含该点的小区域,也被称为窗口 …

在IDEA中使用Git在将多次commit合并为一次commit

案例: 我想要将master分支中的 测试一、测试二、测试三三次commit合并为一次commit 1. 点击Git 2. 双击点击commit所在的分支 3. 右键要合并的多个commit中的第一次提交的commit 4. 点击右键后弹出的菜单中的Interactively Rebase From Here选项 5. 点击测试二…

MySQL排序操作

025排序操作 select .. from .. order by 字段 asc/descselect empno, ename, sal from emp order by sal asc;asc 不写的话,默认升序 多个字段排序 查询员工的编号、姓名、薪资,按照薪资升序排列,如果薪资相同的,再按照姓名升…

二叉树的顺序结构(堆的实现)

前言 普通的二叉树是不适合用数组来存储的,因为可能会存在大量的空间浪费。而完全二叉树更适合使用顺序结 构存储。 现实中我们通常把堆 ( 一种二叉树 ) 使用顺序结构的数组来存储,需要注意的是这里的堆和操作系统 虚拟进程地址空间中的堆是两回事&…

问题:8255A的端口A工作在方式2时,使用端口C的______作为与CPU和外部设备的联络信号。 #媒体#经验分享#其他

问题:8255A的端口A工作在方式2时,使用端口C的______作为与CPU和外部设备的联络信号。 参考答案如图所示

邮件安全证书,保障通信安全的必备利器

在数字通信日益普及的今天,电子邮件的安全性越来越受到人们的关注。邮件安全证书,作为保障邮件通信安全的重要工具,逐渐走进了大众的视野。本文将为大家揭秘邮件安全证书,解答关于它的常见问题,帮助大家更好地了解和使…

浮点数的精度和精度丢失,如何规避,有简单操作

在日常工作中,如果做财务软件相关肯定会遇到这种问题,凭证金额表面上看是相等的,但程序运算出的结果却是FALSE。 例如:验证凭证金额借方总金额是否等于贷方总金额? 直接sum(借方分录金额1.1借方分录金额2.…

RK3568技术笔记之一 RK3568总体介绍

RK3568是瑞芯微开发出一款很好用的芯片。我先把ROCKCHIP的原厂信息搬过来看看。 首先声明一下,这篇文章里的资讯版权归瑞芯微电子股份有限公司。毕竟是我转过来的嘛。 我自己的心得,版权就归我啦。 主要特性 Quad-core Cortex-A55 up to 2.0GHzMali-G…

认识HTTP状态码(status code)

目录 1、200 OK(访问成功)👇 2、404 Not Found (没有找到资源)👇 3、403 Forbidden (访问拒绝)👇 4、405 Method Not Allowed👇 6、504 Gateway Timeout…

CV Method:经典CNN Backbone总结

文章目录 前言一、ResNet二、ResNeXt三、Res2Net四、SeNet五、ResNeSt六、DenseNet七、CSPNetPytorch Model Code总结 前言 Backbone作为一切深度学习任务的基础,不论是理论还是实际应用都有重要的意义,本文针对经典Backbone进行总结,这些Ba…

[word] word怎样转换成pdf #职场发展#经验分享#职场发展

word怎样转换成pdf word怎样转换成pdf?word格式是办公中常会用到的格式,word格式编辑好了要想转换成pdf格式再来传输的话需要怎么操作呢?小编这就给大家分享下操作方法,一起来学习下吧! 1、安装得力PDF转换器&#x…

【stm32/CubeMX、HAL库】swjtu嵌入式实验七 ADC 实验

相关电路与IO引脚 注意&#xff1a;串口打印重定向后使用printf打印需要在keil里勾选 Use MicroLIB &#xff0c;否则会卡住。 参看&#xff1a;https://zhuanlan.zhihu.com/p/565613666 串口重定向&#xff1a; /* USER CODE BEGIN Includes */#include <stdio.h>//…

锐捷校园网自助服务系统 login_judge.jsf 任意文件读取漏洞复现(XVE-2024-2116)

0x01 产品简介 锐捷校园网自助服务系统是锐捷网络推出的一款面向学校和校园网络管理的解决方案。该系统旨在提供便捷的网络自助服务,使学生、教职员工和网络管理员能够更好地管理和利用校园网络资源。 0x02 漏洞概述 校园网自助服务系统/selfservice/selfservice/module/sc…

apollo 环境配置

输入法 安装输入google pinyin法 sudo apt install fcitx-bin sudo apt install fcitx-table sudo apt-get install fcitx fcitx-googlepinyin -y 最后需要reboot 系统环境 修改文件夹名称为英文 将Ubuntu主文件夹里的中文文件夹名称改成英文_番茄炒鸡蛋z的博客-CSDN博客…

java中事务中遇到锁会造成什么问题,以及该如何解决?

在spring中实现事务有多种方式&#xff0c;主要是两种&#xff1a;一种是声明式事务&#xff0c;一种是编程式事务&#xff0c;今天我们就讲声明式事务中的一种&#xff0c;使用注解Transactional&#xff0c;这个注解的作用就是帮助我们在代码执行完毕之后自动提交事务&#x…