在PyTorch中从头开始建立一个简单的神经网络的步骤指南

893 阅读5分钟

PyTorch是构建深度学习模型最常用的库之一,尤其是基于神经网络的模型。在许多与深度学习相关的任务中,我们会发现PyTorch的使用,因为它具有生产就绪分布式训练、强大的生态系统和云支持等特点和能力。在这篇文章中,我们将学习如何使用PyTorch库在短短几步内建立一个简单的神经网络。为此,我们将展示一个实践性的实现,我们将为一个分类问题建立一个简单的神经网络。

  • **第1步:创建数据
  • 2步::使用数据加载器加载数据
  • 第3步:建立一个神经网络模型
    • 定义神经网络类
    • 实例化分类器
  • 4步:训练神经网络模型
    • 优化损失曲线
    • 定义决策边界
  • 第5步:做出预测

让我们从第一步开始,我们将创建一个数据集来实现。

第1步:创建数据

在这篇文章中,我们将了解在PyTorch中定义和运行神经网络的直觉。为此,我们将从头开始建立一个神经网络,并将其应用于一个分类问题。为此,我们将使用sklearn.datasets下的make_classification创建一个数据集,在制作分类数据集时使用。

使用下面几行代码,我们可以创建用于分类的数据集:

from sklearn.datasets import make_classification
X, Y = make_classification(
    n_features=4, n_redundant=0, n_informative=3, n_clusters_per_class=2, n_classes=3
)

使用上面的代码,我们已经创建了一个分类数据集,在这个数据集中,我们有4个特征,3个信息特征和3个类。

让我们来看看这个数据集:

import matplotlib.pyplot as plt
plt.title("Multi-class data, 4 informative features, 3 classes", fontsize="large")
plt.scatter(X[:, 0], X[:, 1], marker="o", c=Y, s=25, edgecolor="k")

在这里,我们可以看到我们的数据集在一个二维空间中,三类的点是清晰可见的。

制作完数据集后,我们就可以建立一个分类模型了。因为在这篇文章中,我们讨论的是使用PyTorch实现一个简单的神经网络,我们将使用一个两层的神经网络,我们可以使用sigmoid作为激活函数。上图中的数据点将是我们的输入坐标,与这些点相关的类是基础事实。

第2步:使用数据加载器加载数据

在定义模型之前,我们需要将我们的数据集分成测试集和训练集。这可以通过以下几行代码来完成:

from sklearn.model_selection import train_test_split
X_train, X_test, Y_train, Y_test = train_test_split(X, Y, test_size=0.33, random_state=42)

让我们检查一下分割后的数据集的形状:

X_train.shape, X_test.shape, Y_train.shape, Y_test.shape

输出:

在这之后,我们需要将训练数据定义为PyTorch张量:

import torch
Y_test = torch.from_numpy(X_test)
Y_test = torch.from_numpy(np.asarray(Y_test))

为了使用数据集的批次,我们需要通过PyTorch的Dataloader模块来放置数据。使用下面几行代码,我们可以做到这一点:

from torch.utils.data import Dataset, DataLoader
class Data(Dataset):
    def __init__(self):
        self.X=torch.from_numpy(X_train)
        self.Y=torch.from_numpy(Y_train)
        self.len=self.X.shape[0]
    def __getitem__(self,index):      
        return self.X[index], self.Y[index]
    def __len__(self):
        return self.len
data=Data()
loader=DataLoader(dataset=data,batch_size=64)

检查张量下的数据的形状:

print(data.X[0:5])
print(data.X.shape)
print(data.Y[0:5])
print(data.Y.shape)

输出:

第3步:建立一个神经网络模型

首先,我们将定义网络的维度:

 input_dim=4     # how many Variables are in the dataset
hidden_dim = 25 # hidden layers
output_dim=3    # number of classes

步骤3.1:定义神经网络类

可以使用以下几行代码来定义一个用于创建简单网络的类:

import torch.nn as nn
class Net(nn.Module):
    def __init__(self,input,H,output):
        super(Net,self).__init__()
        self.linear1=nn.Linear(input,H)
        self.linear2=nn.Linear(H,output)
 
        
    def forward(self,x):
        x=torch.sigmoid(self.linear1(x))  
        x=self.linear2(x)
        return x

步骤3.2:实例化分类器

现在有了上面定义的维度,我们可以使用上一步定义的类来实例化一个模型实例:

clf=Net(input_dim,hidden_dim,output_dim)

让我们检查一下模型的信息

print(clf.parameters)

输出:

在这里我们可以看到,我们准备的模型将以4个特征作为输入,并将给出4个特征作为输出。

第四步:训练神经网络模型

在训练之前,我们需要定义计算参数梯度的准则和更新参数的优化器:

criterion=nn.CrossEntropyLoss()
optimizer=torch.optim.SGD(clf.parameters(), lr=0.1)

在定义了准则和优化器之后,我们就可以训练我们的模型了。使用以下几行代码,我们可以训练它:

learning_rate = 1e-1
loss_list = []
for t in range(1000):
    y_pred = clf(x)
    loss = criterion(y_pred, y)
    loss_list.append(loss.item())
    clf.zero_grad()
    loss.backward()
    with torch.no_grad():
        for param in clf.parameters():
            param -= learning_rate * param.grad

在这个训练中,我们定义了一些方法,这些方法将获得累积梯度为零,将损失附加到损失列表上,并将获得一个新的梯度,并使用反向传播更新参数。

步骤4.1:优化损失曲线

损失曲线会让我们了解模型的性能。

损失曲线的可视化

step = np.linspace(0,1000,1000)
plt.plot(step,np.array(loss_list))

输出:

在上面的输出中,我们可以看到我们的损失曲线已经收敛,利用这个模型我们也可以定义我们的决策边界。

步骤4.2:定义决策边界

params = list(clf.parameters())
w = params[0].detach().numpy()[0]
b = params[1].detach().numpy()[0]
t= params[3].detach().numpy()[0]
plt.scatter(X[:, 0], X[:, 1], c=Y,cmap='jet')
u = np.linspace(X[:, 0].min(), X[:, 0].max(), 2)
plt.plot(u, (0.5-b-w[0]*u)/w[1])
plt.plot(u, (0.5-t-w[0]*u)/w[1])
plt.xlim(X[:, 0].min()-0.5, X[:, 0].max()+0.5)
plt.ylim(X[:, 1].min()-0.5, X[:, 1].max()+0.5)

输出:

在上面的输出中,我们可以看到,我们已经定义了我们的决策边界,而且看起来不错。现在我们可以使用这个模型来进行预测。

进行预测

让我们用训练好的神经网络进行预测:

x_val = torch.from_numpy(X_test)
z=clf(x_val)
yhat=torch.max(z.data,1)
yhat[1]

输出:

在上面的输出中,我们可以看到对给定输入模式的类别标签的预测。使用一些修改,如层数或历时数,我们可以提高我们模型的性能。

最后的话

在这篇文章中,我们已经学会了如何在PyTorch中通过几个步骤定义一个神经网络。我们定义了一个数据集,在这个数据集上我们训练了一个双层的神经网络。我们用这个网络进行分类,并在PyTorch中实现。这也可以作为一个简单的多类分类神经网络的例子。

参考文献