zoukankan      html  css  js  c++  java
  • pytorch实现LeNet5代码小结

    代码一

    训练代码:

    import torch
    import torch.optim as optim
    import torch.nn as nn
    import torch.nn.functional as F
    import torchvision
    import torchvision.transforms as transforms
    
    trainset = torchvision.datasets.MNIST(root='./data', train=True,
                                            download=True, transform=transforms.ToTensor())
    trainloader = torch.utils.data.DataLoader(trainset, batch_size=4,
                                              shuffle=True, num_workers=2)
    
    testset = torchvision.datasets.MNIST(root='./data', train=False,
                                           download=True, transform=transforms.ToTensor())
    testloader = torch.utils.data.DataLoader(testset, batch_size=4,
                                             shuffle=False, num_workers=2)
    
    print("train_data:", trainset.data.size())
    print("train_labels:", trainset.targets.size())
    print("test_data:", testset.data.size())
    
    class Net(nn.Module):
        def __init__(self):
            super(Net, self).__init__()
            self.conv1 = nn.Conv2d(1, 6, 5, 1, 2)
            self.pool = nn.MaxPool2d(2, 2)
            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 = self.pool(F.relu(self.conv1(x)))
            x = self.pool(F.relu(self.conv2(x)))
            x = x.view(x.size()[0], -1)
            x = F.relu(self.fc1(x))
            x = F.relu(self.fc2(x))
            x = self.fc3(x)
            return x
    
    
    net = Net()
    
    criterion = nn.CrossEntropyLoss()
    optimizer = optim.SGD(net.parameters(), lr=0.001, momentum=0.9)
    
    device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")
    print(device)
    net = net.to(device)
    
    for epoch in range(2):
        running_loss = 0.0
        for i, data in enumerate(trainloader, 0):
            inputs, labels = data[0].to(device), data[1].to(device)
            optimizer.zero_grad()
            outputs = net(inputs)
            loss = criterion(outputs, labels)
            loss.backward()
            optimizer.step()
    
            running_loss += loss.item()
            if i % 2000 == 1999:
                print('[%d, %5d] loss: %.3f' %
                      (epoch + 1, i + 1, running_loss / 2000))
                running_loss = 0.0
    
    print('Finished Training')
    

    测试代码:

    correct = 0
    total = 0
    with torch.no_grad():
        for data in testloader:
            images, labels = data[0].to(device), data[1].to(device)
            outputs = net(images)
            _, predicted = torch.max(outputs.data, 1)
            total += labels.size(0)
            correct += (predicted == labels).sum().item()
    
    print('Accuracy of the network on the 10000 test images: %d %%' % (
        100 * correct / total))
    

    代码二

    来源:https://blog.csdn.net/u014453898/article/details/90707987

    训练代码:

    
    import torch
    import torch.nn as nn
    import torch.nn.functional as F
    import torch.optim as optim
    from torchvision import datasets, transforms
    from torch.autograd import Variable
     
     
    lr = 0.01 #学习率
    momentum = 0.5
    log_interval = 10 #跑多少次batch进行一次日志记录
    epochs = 10
    batch_size = 64
    test_batch_size = 1000
     
     
    class LeNet(nn.Module):
        def __init__(self):
            super(LeNet, self).__init__()
            self.conv1 = nn.Sequential(  # input_size=(1*28*28)
                nn.Conv2d(1, 6, 5, 1, 2),  # padding=2保证输入输出尺寸相同
                nn.ReLU(),  # input_size=(6*28*28)
                nn.MaxPool2d(kernel_size=2, stride=2),  # output_size=(6*14*14)
            )
            self.conv2 = nn.Sequential(
                nn.Conv2d(6, 16, 5),
                nn.ReLU(),  # input_size=(16*10*10)
                nn.MaxPool2d(2, 2)  # output_size=(16*5*5)
            )
            self.fc1 = nn.Sequential(
                nn.Linear(16 * 5 * 5, 120),
                nn.ReLU()
            )
            self.fc2 = nn.Sequential(
                nn.Linear(120, 84),
                nn.ReLU()
            )
            self.fc3 = nn.Linear(84, 10)
     
        # 定义前向传播过程,输入为x
        def forward(self, x):
            x = self.conv1(x)
            x = self.conv2(x)
            # nn.Linear()的输入输出都是维度为一的值,所以要把多维度的tensor展平成一维
            x = x.view(x.size()[0], -1)
            x = self.fc1(x)
            x = self.fc2(x)
            x = self.fc3(x)
            return x #F.softmax(x, dim=1)
     
     
     
    def train(epoch):  # 定义每个epoch的训练细节
        model.train()  # 设置为trainning模式
        for batch_idx, (data, target) in enumerate(train_loader):
            data = data.to(device)
            target = target.to(device)
            data, target = Variable(data), Variable(target)  # 把数据转换成Variable
            optimizer.zero_grad()  # 优化器梯度初始化为零
            output = model(data)  # 把数据输入网络并得到输出,即进行前向传播
            loss = F.cross_entropy(output,target)  #交叉熵损失函数
            loss.backward()  # 反向传播梯度
            optimizer.step()  # 结束一次前传+反传之后,更新参数
            if batch_idx % log_interval == 0:  # 准备打印相关信息
                print('Train Epoch: {} [{}/{} ({:.0f}%)]	Loss: {:.6f}'.format(
                    epoch, batch_idx * len(data), len(train_loader.dataset),
                           100. * batch_idx / len(train_loader), loss.item()))
     
     
    def test():
        model.eval()  # 设置为test模式
        test_loss = 0  # 初始化测试损失值为0
        correct = 0  # 初始化预测正确的数据个数为0
        for data, target in test_loader:
     
            data = data.to(device)
            target = target.to(device)
            data, target = Variable(data), Variable(target)  #计算前要把变量变成Variable形式,因为这样子才有梯度
     
            output = model(data)
            test_loss += F.cross_entropy(output, target, size_average=False).item()  # sum up batch loss 把所有loss值进行累加
            pred = output.data.max(1, keepdim=True)[1]  # get the index of the max log-probability
            correct += pred.eq(target.data.view_as(pred)).cpu().sum()  # 对预测正确的数据个数进行累加
     
        test_loss /= len(test_loader.dataset)  # 因为把所有loss值进行过累加,所以最后要除以总得数据长度才得平均loss
        print('
    Test set: Average loss: {:.4f}, Accuracy: {}/{} ({:.0f}%)
    '.format(
            test_loss, correct, len(test_loader.dataset),
            100. * correct / len(test_loader.dataset)))
     
     
     
    if __name__ == '__main__':
        device = torch.device('cuda' if torch.cuda.is_available() else 'cpu') #启用GPU
     
        train_loader = torch.utils.data.DataLoader(  # 加载训练数据
            datasets.MNIST('../data', train=True, download=True,
                           transform=transforms.Compose([
                               transforms.ToTensor(),
                               transforms.Normalize((0.1307,), (0.3081,))  #数据集给出的均值和标准差系数,每个数据集都不同的,都数据集提供方给出的
                           ])),
            batch_size=batch_size, shuffle=True)
     
        test_loader = torch.utils.data.DataLoader(  # 加载训练数据,详细用法参考我的Pytorch打怪路(一)系列-(1)
            datasets.MNIST('../data', train=False, transform=transforms.Compose([
                transforms.ToTensor(),
                transforms.Normalize((0.1307,), (0.3081,)) #数据集给出的均值和标准差系数,每个数据集都不同的,都数据集提供方给出的
            ])),
            batch_size=test_batch_size, shuffle=True)
     
        model = LeNet()  # 实例化一个网络对象
        model = model.to(device)
        optimizer = optim.SGD(model.parameters(), lr=lr, momentum=momentum)  # 初始化优化器
     
        for epoch in range(1, epochs + 1):  # 以epoch为单位进行循环
            train(epoch)
            test()
     
        torch.save(model, 'model.pth') #保存模型
    

    测试代码:

    import torch
    import cv2
    import torch.nn.functional as F
    from modela import LeNet  ##重要,虽然显示灰色(即在次代码中没用到),但若没有引入这个模型代码,加载模型时会找不到模型
    from torch.autograd import Variable
    from torchvision import datasets, transforms
    import numpy as np
     
    if __name__ =='__main__':
        device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')
        model = torch.load('model.pth') #加载模型
        model = model.to(device)
        model.eval()    #把模型转为test模式
     
        img = cv2.imread("3.jpg")  #读取要预测的图片
        trans = transforms.Compose(
            [
                transforms.ToTensor(),
                transforms.Normalize((0.1307,), (0.3081,))
            ])
     
        img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)#图片转为灰度图,因为mnist数据集都是灰度图
        img = trans(img)
        img = img.to(device)
        img = img.unsqueeze(0)  #图片扩展多一维,因为输入到保存的模型中是4维的[batch_size,通道,长,宽],而普通图片只有三维,[通道,长,宽]
        #扩展后,为[1,1,28,28]
        output = model(img)
        prob = F.softmax(output, dim=1)
        prob = Variable(prob)
        prob = prob.cpu().numpy()  #用GPU的数据训练的模型保存的参数都是gpu形式的,要显示则先要转回cpu,再转回numpy模式
        print(prob)  #prob是10个分类的概率
        pred = np.argmax(prob) #选出概率最大的一个
        print(pred.item())
    

    代码三

    来源:https://www.cnblogs.com/denny402/p/7506523.html

    训练代码:

    import torch
    import torchvision
    from torch.autograd import Variable
    import torch.utils.data.dataloader as Data
    
    train_data = torchvision.datasets.MNIST(
        './mnist', train=True, transform=torchvision.transforms.ToTensor(), download=True
    )
    test_data = torchvision.datasets.MNIST(
        './mnist', train=False, transform=torchvision.transforms.ToTensor()
    )
    print("train_data:", train_data.train_data.size())
    print("train_labels:", train_data.train_labels.size())
    print("test_data:", test_data.test_data.size())
    
    train_loader = Data.DataLoader(dataset=train_data, batch_size=64, shuffle=True)
    test_loader = Data.DataLoader(dataset=test_data, batch_size=64)
    
    
    class Net(torch.nn.Module):
        def __init__(self):
            super(Net, self).__init__()
            self.conv1 = torch.nn.Sequential(
                torch.nn.Conv2d(1, 32, 3, 1, 1),
                torch.nn.ReLU(),
                torch.nn.MaxPool2d(2))
            self.conv2 = torch.nn.Sequential(
                torch.nn.Conv2d(32, 64, 3, 1, 1),
                torch.nn.ReLU(),
                torch.nn.MaxPool2d(2)
            )
            self.conv3 = torch.nn.Sequential(
                torch.nn.Conv2d(64, 64, 3, 1, 1),
                torch.nn.ReLU(),
                torch.nn.MaxPool2d(2)
            )
            self.dense = torch.nn.Sequential(
                torch.nn.Linear(64 * 3 * 3, 128),
                torch.nn.ReLU(),
                torch.nn.Linear(128, 10)
            )
    
        def forward(self, x):
            conv1_out = self.conv1(x)
            conv2_out = self.conv2(conv1_out)
            conv3_out = self.conv3(conv2_out)
            res = conv3_out.view(conv3_out.size(0), -1)
            out = self.dense(res)
            return out
    
    
    model = Net()
    print(model)
    
    optimizer = torch.optim.Adam(model.parameters())
    loss_func = torch.nn.CrossEntropyLoss()
    
    for epoch in range(10):
        print('epoch {}'.format(epoch + 1))
        # training-----------------------------
        train_loss = 0.
        train_acc = 0.
        for batch_x, batch_y in train_loader:
            batch_x, batch_y = Variable(batch_x), Variable(batch_y)
            out = model(batch_x)
            loss = loss_func(out, batch_y)
            train_loss += loss.data[0]
            pred = torch.max(out, 1)[1]
            train_correct = (pred == batch_y).sum()
            train_acc += train_correct.data[0]
            optimizer.zero_grad()
            loss.backward()
            optimizer.step()
        print('Train Loss: {:.6f}, Acc: {:.6f}'.format(train_loss / (len(
            train_data)), train_acc / (len(train_data))))
    

    测试代码:

    model.eval()
        eval_loss = 0.
        eval_acc = 0.
        for batch_x, batch_y in test_loader:
            batch_x, batch_y = Variable(batch_x, volatile=True), Variable(batch_y, volatile=True)
            out = model(batch_x)
            loss = loss_func(out, batch_y)
            eval_loss += loss.data[0]
            pred = torch.max(out, 1)[1]
            num_correct = (pred == batch_y).sum()
            eval_acc += num_correct.data[0]
        print('Test Loss: {:.6f}, Acc: {:.6f}'.format(eval_loss / (len(
            test_data)), eval_acc / (len(test_data))))
    
  • 相关阅读:
    剑指Offer(Java版)第四十六题:输出所有和为S的连续正数序列。序列内按照从小至大的顺序,序列间按照开始数字从小到大的顺序。
    剑指Offer(Java版)第四十五题:一个整型数组里除了两个数字之外,其他的数字都出现了两次。请写程序找出这两个只出现一次的数字。
    剑指Offer(Java版)第四十四题:输入一棵二叉树,判断该二叉树是否是平衡二叉树。
    剑指Offer(Java版)第四十三题:输入一棵二叉树,求该树的深度。 从根结点到叶结点依次经过的结点 (含根、叶结点)形成树的一条路径, 最长路径的长度为树的深度。
    剑指Offer(Java版)第四十二题:统计一个数字在排序数组中出现的次数。
    剑指Offer(Java版)第四十一题:输入两个链表,找出它们的第一个公共结点。
    剑指Offer(Java版)第四十题:在数组中的两个数字,如果前面一个数字大于后面的数字, 则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。 并将P对1000000007取模的结果输出。 即输出P%1000000007
    剑指Offer(Java版)第三十九题:在一个字符串(0<=字符串长度<=10000,全部由字母组成)中找到第一个只出现一次的字符, 并返回它的位置, 如果没有则返回 -1(需要区分大小写).
    剑指Offer(Java版)第三十八题:把只包含质因子2、3和5的数称作丑数(Ugly Number)。 例如6、8都是丑数,但14不是,因为它包含质因子7。 习惯上我们把1当做是第一个丑数。 求按从小到大的顺序的第N个丑数。
    【微信支付】退款
  • 原文地址:https://www.cnblogs.com/lokvahkoor/p/12240599.html
Copyright © 2011-2022 走看看