2021-09-25

PyTorch深度学习:一小时入门

  1. 神经网络 使用 torch.nn 包可以进行神经网络的构建。 现在你对autograd有了初步的了解,而nn建立在autograd的基础上来进行模型的定义和微分。
    nn.Module中包含着神经网络的层,同时forward(input)方法能够将output进行返回。
    举个例子,来看一下这个数字图像分类的神经网络。 这是一个简单的前馈神经网络。从前面获取到输入的结果,从一层传递到另一层,最后输出最后结果。 一个典型的神经网络的训练过程是这样的:
    定义一个有着可学习的参数(或者权重)的神经网络 对着一个输入的数据集进行迭代: 用神经网络对输入进行处理 计算代价值 (对输出值的修正到底有多少) 将梯度传播回神经网络的参数中 更新网络中的权重 通常使用简单的更新规则: weight = weight + learning_rate * gradient

在这里插入图片描述

import torch
import torch.nn as nn
import torch.nn.functional as F
 #Variable就是 变量 的意思
from torch.autograd import Variable
import torch.optim as optim
import torchvision
import torchvision.transforms as transforms
import pylab
import matplotlib.pyplot as plt
import numpy as np



#==============一、让我们来定义一个LeNet神经网络:==================
class Net(nn.Module):    #接收的输入是nn.Module
    #构造函数就是自己定义的一些运算层,参数是随机初始化的
    def __init__(self):
        super(Net,self).__init__()
        self.conv1 = nn.Conv2d(1,6,5)  # 1 input image channel, 6 output channels, 5x5 square convolution kernel
        self.conv2 = nn.Conv2d(6,16,5)
        self.fc1 = nn.Linear(16*5*5 ,120)# an affine operation: y = Wx + b
        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))# Max pooling over a (2, 2) window
        x = F.max_pool2d(F.relu(self.conv2(x)), 2)  # If the size is a square you can only specify a single number
        x = x.view(-1, self.num_flat_features(x))
        x = F.relu(self.fc1(x))
        x = F.relu(self.fc2(x))
        x = self.fc3(x)
        return x

    def num_flat_features(self, x):
        size = x.size()[1:] # all dimensions except the batch dimension
        print("size==",size)
        num_features = 1
        for s in size:
            num_features *= s
        return num_features

net = Net()
print(net)


""""
仅仅需要定义一个forward函数就可以了,backward会自动地生成。
你可以在forward函数中使用所有的Tensor中的操作。
模型中可学习的参数会由net.parameters()返回。"""



params = list(net.parameters())
print(len(params))
print(params[0].size()) # conv1's .weight

input =Variable(torch.randn(1, 1, 32, 32))   #输入到模型中做前向计算的一定是一个Variable
out = net(input)

#接着初始化网络中所有参数的梯度,然后用随机的梯度做一次反向传播
net.zero_grad() # 对所有的参数的梯度缓冲区进行归零,
out.backward(torch.randn(1, 10)) # 使用随机的梯度进行反向传播


#通过预期值和实际值求loss
# 神经网络的参数是要用训练数据去训练的,这就需要定义loss funtion,pytorch中的nn模块内定义了各种loss function,
# torch中的loss function 包含输出和目标值。手写体字符有10个元素,我们就用1-10来表示,定义loss如下:
output = net(input)
target = Variable(torch.arange(1, 11))  # a dummy target, for example
target = target.view(1, -1)  # make it the same shape as output   就是和numpy里的reshape是一样的,output不改变数据,但是改变数据的形状,1是表示一列,最后得到的是一个列tensor
criterion = nn.MSELoss()    #求predict = output和target之间的loss。
loss = criterion(output, target)
print("loss:",loss)
"""Pytorch里面的X.view(-1)操作:  X.view(-1)中的-1本意是根据另外一个数来自动调整维度,但是这里只有一个维度,因此就会将X里面的所有维度数据转化成一维的,并且按先后顺序排列。"""
#更新optimizer 优化器
#利用loss做一次反向传播就可以求出所有参数的梯度值,一般在计算定义loss后,先初始化所有参数的梯度值,再更新梯度。
# 我们知道,梯度下降法只是求解优化问题中的参数的一种方法。其他方法还有Adam, RMSProp等。
# create your optimizer 优化器
optimizer = optim.SGD(net.parameters(), lr=0.01)   #net.parameters()网络中所有参数  lr=0.01学习率

# in your training loop:训练循环
optimizer.zero_grad()   # zero the gradient buffers# 对所有的参数的梯度缓冲区进行归零,
output = net(input)
loss = criterion(output.to(torch.float32), target.to(torch.float32))#易报错:做类型转换
loss.backward()
m = optimizer.step()  # 所有的optimizer都实现了step()方法,这个方法会更新所有的参数
print("优化过程--------------------",m)



"""=======二、简单的分类网络架构=============="""
#一个完整的分类网络包括:读取数据→展示数据样例→定义网络结构→定义loss和优化方法→训练网络→测试网络。以CIFAR10为例


#下载数据集
transform = transforms.Compose(
    [transforms.ToTensor(),
     transforms.Normalize(mean=(0.5, 0.5, 0.5), std=(0.5, 0.5, 0.5))])  #前面的(0.5,0.5,0.5) 是 R G B 三个通道上的均值, 后面(0.5, 0.5, 0.5)是三个通道的标准差std,
"""注意通道顺序是 R G B ,用过opencv的同学应该知道openCV读出来的图像是 BRG顺序。这两个tuple数据是用来对RGB 图像做归一化的,如其名称 Normalize 所示这里都取0.5只是一个近似的操作,实际上其均值和方差并不是这么多,但是就这个示例而言 影响可不计。"""
batch_size=4
# !!!!!!!!!!!!    数据集下载完后,改程序段,将download改为False     !!!!!!!!!!!!!!
trainset = torchvision.datasets.CIFAR10(root='./data', train=True,download=False, transform=transform)  #download,表示是否自动下载cifar数据集 ,train,表示是否加载数据库的训练集,False的时候加载测试集; transform,表示是否需要对数据进行预处理,none为不进行预处理;;
trainloader = torch.utils.data.DataLoader(trainset, batch_size=batch_size,shuffle=True, num_workers=2)
testset = torchvision.datasets.CIFAR10(root='./data', train=False,
                                       download=False, transform=transform)#download=False,表示不自动下载
testloader = torch.utils.data.DataLoader(dataset=testset, batch_size=batch_size,
                                         shuffle=False, num_workers=2)   #um_workers=0意思大概就是不使用多进程 ,设置为2,就是同时跑两个进程,加快数据加载速度

classes = ('plane', 'car', 'bird', 'cat','deer', 'dog', 'frog', 'horse', 'ship', 'truck')#10分类

简单的分类网络架构

# 定义图像显示函数
def imshow(img):
    print("shape-1----", np.shape(images))
    img = img / 2 + 0.5     # 非标准的 unnormalize;因为归一话的时候是先减去平均值0.5 ,然后再除以标准偏差0.5;那么反归一化就是先乘以0.5,再加0.5。
    print("shape-2----", np.shape(images))  #torch.Size([4, 3, 32, 32])即取前四张图片,每张3通道尺寸是32*32图片
    npimg = img.numpy()   # 将torch.FloatTensor 转换为numpy

    plt.imshow(np.transpose(npimg, (1, 2, 0)))   #x.transpose(1, 2, 0),其实就是将x第二维度挪到第一维上,第三维移到第二维上,原本的第一维移动到第三维上,最后的shape为:(3,2,2),因为在plt.imshow在现实的时候输入的是(imagesize,imagesize,channels),而def imshow(img,text,should_save=False)中,参数img的格式为(channels,imagesize,imagesize),这两者的格式不一致,
    pylab.show()
    print("shape-4----", np.shape(npimg))

得到一些随机的训练图像

if __name__ == '__main__' :          #加if __name__ == '__main__' :意思是调用当前模块时,不执行下面的内容,这样用多进程就不会报错了。
    dataiter = iter(trainloader)
    images, labels = dataiter.next()
   # print("shape-1----",np.shape(images))
    # show images
    imshow(torchvision.utils.make_grid(images))  #make_grid的作用是将若干幅图像按照网格排列的方式拼成一幅图像 torch.Size([4, 3, 32, 32])---- (3, 34+2+2, 32X4),方法默认:make_grid(images,padding=2)
    # 打印标签

    print(' '.join('%5s' % classes[labels[j]] for j in range(batch_size)))   #.join返回通过指定字符连接序列中元素后生成的新字符串。

在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
使用python的pymsql完成如下:表结构与数据创建 1. 建立 `users` 表和 `orders` 表。 `users` 表有用户ID、用户名、年龄字段,(id,name,age) `orders` 表有订单ID、订单日期、订单金额,用户id字段。(id,order_date,amount,user_id) 2 两表的id作为主键,`orders` 表用户id为users的外键 3 插入数据 `users` (1, '张三', 18), (2, '李四', 20), (3, '王五', 22), (4, '赵六', 25), (5, '钱七', 28); `orders` (1, '2021-09-01', 500, 1), (2, '2021-09-02', 1000, 2), (3, '2021-09-03', 600, 3), (4, '2021-09-04', 800, 4), (5, '2021-09-05', 1500, 5), (6, '2021-09-06', 1200, 3), (7, '2021-09-07', 2000, 1), (8, '2021-09-08', 300, 2), (9, '2021-09-09', 700, 5), (10, '2021-09-10', 900, 4); 查询语句 1. 查询订单总金额 2. 查询所有用户的平均年龄,并将结果四舍五入保留两位小数。 3. 查询订单总数最多的用户的姓名和订单总数。 4. 查询所有不重复的年龄。 5. 查询订单日期在2021年9月1日至9月4日之间的订单总金额。 6. 查询年龄不大于25岁的用户的订单数量,并按照降序排序。 7. 查询订单总金额排名前3的用户的姓名和订单总金额。 8. 查询订单总金额最大的用户的姓名和订单总金额。 9. 查询订单总金额最小的用户的姓名和订单总金额。 10. 查询所有名字含有“李”的用户,按照名字升序排序。 11. 查询所有年龄大于20岁的用户,按照年龄降序排序,并只显示前5条记录。 12. 查询每个用户的订单数量和订单总金额,并按照总金额降序排序。
最新发布
06-03
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值