Pytorch 之 PolyRegression

13 篇文章 0 订阅
10 篇文章 0 订阅

PloyRegression:在 notebook上用代码块来实现

导入一些常常用的包:

import torch
import numpy as np
from torch.autograd import Variable
from torch import nn,optim
import matplotlib.pyplot as plt

数据的准备阶段:

def make_features(x): # 定义函数,来随机先产生一个[x,x^2,x^3],通过代码x.unsqueeze(1),增加了一个维度,变成[[x],[x^2],[x^3]]
    x = x.unsqueeze(1)
    return torch.cat([x ** i for i in range(1,4)],dim = 1)

设置权重,系数和偏置:在这里,我明白了取[[0.5],[3],[2.4]]中2.4是[2][0]这种方式!!

w_target = torch.FloatTensor([0.5,3,2.4]).unsqueeze(1)  # 变成二维的[[0.5],[3],[2.4]]
b_target = torch.FloatTensor([0.9])

定义要拟合的多项式:.mm()表示矩阵的相乘

def f(x):   # 定义要拟合的函数
    return x.mm(w_target) + b_target[0]  #一维的时候[0]来将数值取出来

定义批量取数据的函数,随机产生x,计算得到y

通过 torch.randn产生无序的数据,要画图的时候,要进行排序,一旦排序.sort(),就

将Tensor变成了numpy.array的形式,在进入make_features()的时候,无法增加

维度,需要进行转变

def get_batch(batch_size = 32): # 随一批产生32个数
    random = torch.randn(batch_size)
    random = np.sort(random)  # 画图要进行排序
    random = torch.from_numpy(random)  #!!这一行代码很重要,他说明了Torch中的Tensor和numpy中的array具有不同的属性,能进行的操作也是不同的
    x = make_features(random)  # 将随机产生的数进行增加维度,并且进行平方、三次方
    y = f(x)  # 得到f(x)
    if torch.cuda.is_available():  # 将Tensor转变成Variable,因为进入模型进行线性层,进行优化的时候,要求是变量类型的
        return Variable(x).cuda(),Variable(y).cuda()
    else:
        return Variable(x),Variable(y)

准备好数据集后,建立模型,训练参数,nn.Linear(),模型里有前向传播

class poly_model(nn.Module): # 继承父类
    def __init__(self):  # 继承父类,必须进行初始化
        super(poly_model,self).__init__()  # 将self理解成子类的对象,对象可以添加相应的的方法和属性
        self.poly = nn.Linear(3,1)  # 关键部分,进行拟合的核心,用到了线性层
        
    def forward(self,x):  # 前向传播
        out = self.poly(x)
        return out

下面应该算是创建模型的对象:

if torch.cuda.is_available():
    model = poly_model().cuda()
else:
    model = poly_model()

在建立模型后,要创建模型的对象;之后要定义损失函数和优化器:

criterion = nn.MSELoss()
optimizer = optim.SGD(model.parameters(),lr = 1e-3)

前面全部是进行的准备工作,接下来是进行的模型的训练

epoch = 0
while True:
    # Get data
    batch_x, batch_y = get_batch()  # 1. 获取训练数据集

    # Forward pass
    output = model(batch_x)  # 2.将数据丢进模型,得到一个模型认为的输出
    
    loss = criterion(output, batch_y)  # 3.进入损失函数,进行输出的更新
    print_loss = loss.item()
    
    # Reset gradients
    optimizer.zero_grad()  # 要进行一个梯度的更新,必须先把梯度进行清零
    
    # Backward pass
    loss.backward()   # 后向传播 ,从输出到输入,对每个神经元进行参数的更新,实际上就是求导的过程
    
    # update parameters
    optimizer.step()  # 更新参数
    
    epoch += 1
    if print_loss < 1e-4:  # 实际上,这行代码很关键,它控制着训练的结束
            break

这里好好理解对模型学习到的系数的提取model.poly.weight[0][1]

print("Loss:{:.6f} after {} batches".format(loss.item(),epoch))
print("==>> Learned function:y = {:.2f}* x+{:.2f}* x^2 + {:.2f}* x^3 +{:.2f}".format(model.poly.weight[0][1],model.poly.weight[0][1],model.poly.weight[0][2],model.poly.bias[0]))
print("==>> Learned function: y = {:.2f}* x+{:.2f}* x^2 + {:.2f}* x^3 + {:.2f}".format(w_target[0][0],w_target[1][0],w_target[2][0],b_target[0]))
Loss:0.000089 after 3669 batches
==>> Learned function:y = 3.00* x+3.00* x^2 + 2.40* x^3 +0.91
==>> Learned function: y = 0.50* x+3.00* x^2 + 2.40* x^3 + 0.90

对训练的结果进行可视化,即进行预测,在可视化的过程中,通常有.cpu(),具体好像是在转可

视化的时候是用的numpy,在进行转化的过程中必须在cpu模式下面。

predict = model(batch_x)
batch_x = batch_x.cpu()
batch_y = batch_y.cpu()

x = batch_x.numpy()[:,0]  # 对所有的行进行只取第一列,即x,不是x^2和x^3
plt.plot(x,batch_y.numpy(),'ro') # 红色的圆圈是原来的训练集

predict = predict.cpu()
predict = predict.data.numpy()

plt.plot(x,predict,'b') # 蓝色是进行的预测的
plt.show()

在这里插入图片描述

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值