Advertisement

深度神经网络(DNN)

阅读量:

输入特征与输出特征几个代表有几个神经元

2.输入层自身没有内部参数(零号层)。其中包含权重w和偏置b这两个基本元素。例如包括网络层数、各隐藏层的节点数量、所使用的激活函数类型以及学习率(超参数)。

3.batch——size(一般设置为2的幂次)

批量梯度下降(BGD):把所有样本一次性输入网络

随机梯度下降(SGD):每次仅将单个样本输入网络,在每次迭代时更新模型参数(其收敛性较差,在最优解附近可能存在振荡现象)。

小批量梯度下降(MBGD):中和上述两种

one-hot 编码是最容易理解的方法-博客

DNN的实现

复制代码
 #jupyter notebook

    
  
    
 import torch
    
 import torch.nn as nn
    
 import matplotlib.pyplot as plt
    
 %matplotlib inline
    
  
    
 # 展示高清图
    
 from matplotlib_inline import backend_inline
    
 backend_inline.set_matplotlib_formats('svg')
    
  
    
 '''在训练之前,要准备好训练集的样本。
    
 这里生成 10000 个样本,设定 3 个输入特征与 3 个输出特征,其中
    
 ⚫ 每个输入特征相互独立,均服从均匀分布;
    
 ⚫ 当(X1+X2+X3)< 1 时,Y1 为 1,否则 Y1 为 0;
    
 ⚫ 当 1<(X1+X2+X3)<2 时,Y2 为 1,否则 Y2 为 0;
    
 ⚫ 当(X1+X2+X3)>2 时,Y3 为 1,否则 Y3 为 0;
    
 ⚫ .float()将布尔型张量转化为浮点型张量。'''
    
  
    
 # 生成数据集
    
 X1 = torch.rand(10000,1) # 输入特征 1
    
 X2 = torch.rand(10000,1) # 输入特征 2
    
 X3 = torch.rand(10000,1) # 输入特征 3
    
 Y1 = ( (X1+X2+X3)<1 ).float() # 输出特征 1
    
 Y2 = ( (1<(X1+X2+X3)) & ((X1+X2+X3)<2) ).float() # 输出特征 2
    
 Y3 = ( (X1+X2+X3)>2 ).float() # 输出特征 3
    
 Data = torch.cat([X1,X2,X3,Y1,Y2,Y3],axis=1) # 整合数据集
    
 Data = Data.to('cuda:0') # 把数据集搬到 GPU 上
    
 Data.shape
    
  
    
 # 划分训练集与测试集
    
 train_size = int(len(Data) * 0.7) # 训练集的样本数量
    
 test_size = len(Data) - train_size # 测试集的样本数量
    
 Data = Data[torch.randperm( Data.size(0)) , : ] # 打乱样本的顺序
    
 train_Data = Data[ : train_size , : ] # 训练集样本
    
 test_Data = Data[ train_size : , : ] # 测试集样本
    
 train_Data.shape, test_Data.shape
    
  
    
 class DNN(nn.Module):
    
 def __init__(self):
    
 ''' 搭建神经网络各层 '''
    
 super(DNN,self).__init__()
    
 self.net = nn.Sequential( # 按顺序搭建各层
    
 nn.Linear(3, 5), nn.ReLU(), # 第 1 层:全连接层
    
 nn.Linear(5, 5), nn.ReLU(), # 第 2 层:全连接层
    
 nn.Linear(5, 5), nn.ReLU(), # 第 3 层:全连接层
    
 nn.Linear(5, 3) # 第 4 层:全连接层
    
 )
    
 def forward(self, x):
    
 ''' 前向传播 '''
    
 y = self.net(x) # x 即输入数据
    
 return y # y 即输出数据
    
  
    
 model = DNN().to('cuda:0') # 创建子类的实例,并搬到 GPU 上
    
 model # 查看该实例的各层

网络的外部参数

外部参数即称为超参数,在调参者往往将其视为关键要素进行深入研究和配置。在搭建神经网络模型时涉及的各种超参数包括:各层的不同激活函数类型、各隐藏层节点数量的选择范围以及其对应的初始化值设置等细节因素。在训练神经网络模型时需要考虑的各种超参数包括:损失函数选择的标准依据及其计算方式、学习率调节策略的具体实现路径以及对应的批量大小设定和迭代周期安排等多个维度的关键指标因素。

learning_rate = 0.01 # 定义学习率
optimizer = torch.optim.SGD(model.parameters(), lr=learning_rate) # 使用torch.optim库中的SGD优化器来优化模型参数,并将学习率设置为learning_rate的值

该库仅限于批量或小批量梯度下降方法,在处理单个样本时不可行。此 torch.optim.SGD 仅用于梯度下降方法,请参阅第4章至第5章以获取详细信息。

训练网络

复制代码
 # 训练网络

    
 epochs = 1000
    
 losses = [] # 记录损失函数变化的列表
    
 # 给训练集划分输入与输出
    
 X = train_Data[ : , :3 ] # 前 3 列为输入特征
    
 Y = train_Data[ : , -3: ] # 后 3 列为输出特征
    
 for epoch in range(epochs):
    
 Pred = model(X) # 一次前向传播(批量)
    
 loss = loss_fn(Pred, Y) # 计算损失函数
    
 losses.append(loss.item()) # 记录损失函数的变化,loss.item将张量退化为普通元素
    
 optimizer.zero_grad() # 清理上一轮滞留的梯度
    
 loss.backward() # 一次反向传播
    
 optimizer.step() # 优化内部参数
    
 Fig = plt.figure()
    
 plt.plot(range(epochs), losses)
    
 plt.ylabel('loss'), plt.xlabel('epoch')
    
 plt.show()

测试网络

在测试阶段只需让测试集执行一次前向传播即可,在此局部无需计算梯度。为此可以在该区域关闭梯度,请参考以下代码实现:

复制代码
 # 测试网络

    
 # 给测试集划分输入与输出
    
 X = test_Data[:, :3] # 前 3 列为输入特征
    
 Y = test_Data[:, -3:] # 后 3 列为输出特征
    
 with torch.no_grad(): # 该局部关闭梯度计算功能
    
 Pred = model(X) # 一次前向传播(批量)
    
 Pred[:,torch.argmax(Pred, axis=1)] = 1
    
 Pred[Pred!=1] = 0
    
 correct = torch.sum( (Pred == Y).all(1) ) # 预测正确的样本
    
 total = Y.size(0) # 全部的样本数量
    
 print(f'测试集精准度: {100*correct/total} %')

在计算correct时需要花一些心思。第一步是将(Pred == Y)用于比较预测输出与真实输出在每个元素上的一致性,并返回一个形状为3000×3的布尔型张量。第二步是对这个布尔张量进行(all)(1)运算以检查每一行的三个值是否均为True——如果是,则结果为True;否则为False。(all)(1)表示按"行"方向扫描整个张量,并最终得到一个长度为3000的一阶张量。最后一步则是对这些全True的结果进行求和运算:将所有全True的结果相加起来就能得出正确预测的数量

保存网络:将预训练模型持久化至本地文件 model.pth 中

导入网络:# 加载预训练好的 PyTorch 模型至新网络实例
new_model = torch.load('model.pth')

全部评论 (0)

还没有任何评论哟~