CIFAR-10 简单分类

# 加载数据及预处理
import torch as t
import torchvision as tv
import torchvision.transforms as transforms
from torchvision.transforms import ToPILImage
from torch.autograd import Variable
show = ToPILImage() #可以把tensor转为image

# 第一次运行程序torchvision会自动下载CIFAR-10数据集
# 若已下载,可通过root参数指定

#定义对数据的预处理
transform = transforms.Compose([
            transforms.ToTensor(), # 转为Tensor,把灰度范围从0-255变换到0-1,归一化
            transforms.Normalize((0.5,0.5,0.5),(0.5,0.5,0.5) ) #把0-1变为-1到1,标准化
                                ])

# 训练集
trainset = tv.datasets.CIFAR10(
                                root= "E:/learn/CIFAR-10/data/",
                                train= True,
                                download= True,
                                transform= transform)

trainloader = t.utils.data.DataLoader(   #主要用来将自定义的数据读取接口的输出或者PyTorch已有的数据读取接口的输入按照batch size封装成Tensor,
                                            # 后续只需要再包装成Variable即可作为模型的输入
                                        trainset,
                                        batch_size = 4,
                                        shuffle = True,
                                        num_workers = 0  #多线程
                                     )

#测试集
testset = tv.datasets.CIFAR10(
                                root= "E:/learn/CIFAR-10/data/",
                                train= False,
                                download= True,
                                transform= transform )

testloader = t.utils.data.DataLoader(
                                        trainset,
                                        batch_size = 4,
                                        shuffle = False,
                                        num_workers = 0)

classes = ("plane","car","bird","cat","deer","dog","frog","horse","ship","truck")


#定义网络

import torch.nn as nn
import torch.nn.functional as F

class Net(nn.Module):
    # 把网络中具有可学习参数的层放在构造函数__inif__中
    def __init__(self):
        # 下式等价于nn.Module.__init__.(self)
        super(Net,self).__init__()
        self.conv1 = nn.Conv2d(3,6,5)      # 输入3通道,输出6通道,卷积核为5*5
        self.conv2 = nn.Conv2d(6,16,5)
        self.fc1 = nn.Linear(16*5*5,120)
        self.fc2 = nn.Linear(120,84)
        self.fc3 = nn.Linear(84,10)

    def forward(self,x):
        x = F.max_pool2d(F.relu(self.conv1(x)),(2,2))  # 卷积->激活->池化  3*32*32 —> 6*28*28 -> 6*14*14
        x = F.max_pool2d(F.relu(self.conv2(x)), 2)  # 6*14*14 -> 16*10*10 -> 16*5*5
        x = x.view(x.size()[0],-1)  # 将16*5*5的tensor打平成1维,400
        x = F.relu(self.fc1(x))  # 全连接层 400 -> 120
        x = F.relu(self.fc2(x))  # 全连接层 120 -> 84
        x = self.fc3(x)  # 全连接层 84 -> 10
        return x
net = Net()
print (net)

# 定义损失函数和优化器

from torch import optim

criterion = nn.CrossEntropyLoss() # 交叉熵损失函数
optimizer = optim.SGD(net.parameters(), lr= 0.001, momentum= 0.9)  # 优化器:随机梯度下降

# 训练网络

for epoch in range(2): #训练2次
    running_loss = 0.0
    for i ,data in enumerate(trainloader,0):
        #enumerate() 函数:用于将一个可遍历的数据对象(如列表、元组或字符串)组合为一个索引序列,同时列出数据和数据下标,一般用在 for 循环当中
        #enumerate(sequence, [start=0])
        #sequence -- 一个序列、迭代器或其他支持迭代对象。
        #start -- 下标起始位置。

        # 输入数据
        inputs , labels = data
        inputs, labels = Variable(inputs) , Variable(labels)

        # 梯度清零
        optimizer.zero_grad()

        # forward + backward
        outputs = net(inputs)
        loss = criterion(outputs , labels)  #计算单个batch误差
        loss.backward()  #反向传播

        # 更新参数
        optimizer.step()

        #打印log信息
        running_loss += loss.item()  #2000个batch的误差和
        if i % 2000 ==1999:  #每2000个batch打印一次训练状态
            print("[%d,%5d] loss: %.3f" \
                  % (epoch+1 , i+1 , running_loss / 2000))
            running_loss = 0.0
print("Finished Training")

# 测试网络

dataiter = iter(testloader)  #采用iter(dataloader)返回的是一个迭代器,然后可以使用next()访问。iter(dataloader)访问时,
                                # imgs在前,labels在后,分别表示:图像转换0~1之间的值,labels为标签值。并且imgs和labels是按批次进行输入的。
images , labels = dataiter.next()
print("实际的label:"," ".join(\
            "%08s"%classes[labels[j]] for j in range(4)))
show (tv.utils.make_grid(images / 2 - 0.5)).resize((400,100))

# 计算图片在每个类别上的分数
outputs = net(Variable(images))

# 得分最高的那个类
_, predicted = t.max(outputs.data , 1)  #torch.max()返回两个值,第一个值是具体的value,,也就是输出的最大值(我们用下划线_表示 ,指概率),
                                        # 第二个值是value所在的index(也就是predicted , 指类别)
                                        #选用下划线代表不需要用到的变量
                                        #数字1:其实可以写为dim=1,表示输出所在行的最大值,若改写成dim=0则输出所在列的最大值
print("预测结果:"," ".join("%5s"\
            %classes[predicted[j]] for j in range(4)))

correct = 0  #预测正确图片数
total = 0  #总图片数
for data in testloader:
    images, labels = data
    outputs = net(Variable(images))
    _, predicted = t.max(outputs.data, 1)
    total += labels.size(0)
    correct += (predicted == labels).sum()
print("10000张测试集中的准确率为:%d %%" % (100*correct / total))

#gpu加速
if t.cuda.is_available():
    net.cuda()
    images = images.cuda()
    labels = labels.cuda()
    outputs = net(Variable(images))
    loss = criterion(outputs, Variable(labels))
  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
卷积神经网络(Convolutional Neural Network,CNN)是一种在图像识别、自然语言处理等领域广泛应用的深度学习模型。在cifar-10图像分类任务中,我们可以使用CNN来实现高效准确的图像分类。 首先,我们需要准备cifar-10数据集。该数据集包含了10个类别的60000张32x32像素的彩色图像,其中50000张用于训练,10000张用于测试。我们可以使用Python的Keras库来加载数据集。 然后,我们可以定义一个CNN模型来对图像进行分类。该模型通常由多个卷积层和池化层组成。卷积层用于提取图像的特征,池化层用于减小特征图的大小。在最后一层之后,我们可以添加一个全连接层和一个softmax层来输出每个类别的概率分布。 下面是一个简单的CNN模型实现: ```python from keras.models import Sequential from keras.layers import Conv2D, MaxPooling2D, Flatten, Dense model = Sequential() # 第一层卷积层 model.add(Conv2D(32, (3, 3), activation='relu', input_shape=(32, 32, 3))) # 第一层池化层 model.add(MaxPooling2D(pool_size=(2, 2))) # 第二层卷积层 model.add(Conv2D(64, (3, 3), activation='relu')) # 第二层池化层 model.add(MaxPooling2D(pool_size=(2, 2))) # 第三层卷积层 model.add(Conv2D(64, (3, 3), activation='relu')) # 全连接层 model.add(Flatten()) model.add(Dense(64, activation='relu')) model.add(Dense(10, activation='softmax')) ``` 接下来,我们可以编译模型并训练数据集: ```python model.compile(optimizer='adam', loss='categorical_crossentropy', metrics=['accuracy']) model.fit(x_train, y_train, epochs=10, batch_size=64, validation_data=(x_test, y_test)) ``` 在训练完成后,我们可以使用测试集对模型进行评估: ```python loss, accuracy = model.evaluate(x_test, y_test) print('Test loss:', loss) print('Test accuracy:', accuracy) ``` 通过调整CNN的架构和超参数,我们可以进一步提高模型的准确率。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值