利用pytorch搭建你的神经网络
1、理解pytorch中Numpy、Tensor与Variable
Numpy是一个数学库,主要用于数组的计算。而我们使用Numpy也是可以手动去编写神经网络进行反向传播深度学习的,但是有两个问题,一是利用Numpy手动去编写神经网络很繁琐,代码量较大,不利于大规模开发;二是Numpy是利用CPU运算,而无法直接使用GPU加速计算。
Tensor,中文名叫张量,如果一个物理量,在物体的某个位置上只是一个单值,那么就是普通的标量,比如密度。如果它在同一个位置、从不同的方向上看,有不同的值,而且这个数恰好可以用矩阵乘观察方向来算出来,就是张量。几何代数中定义的张量是基于向量和矩阵的推广,通俗一点理解的话,我们可以将标量视为零阶张量,矢量视为一阶张量,那么矩阵就是二阶张量。
在PyTorch中,Tensor是重要的数据结构,可认为是一个高维数组。Tensor和Numpy中的ndarrays类似,但Tensor可以使用GPU进行加速计算。PyTorch中有许多不同的方法可以创建Tensor或者将Numpy数据转换成Tensor。
PyTorch为了实现GPU加速功能,引入了Tensor,为了实现自动求导功能引入了Variable。顾名思义,Variable就是 变量 的意思。实质上也就是可以变化的量,区别于int变量,它是一种可以变化的变量,这正好就符合了反向传播,参数更新的属性。在torch中的Variable就是一个存放会变化的值的地理位置。里面的值会不停发生变化,就像一个装鸡蛋的篮子,鸡蛋数会不断发生变化。那谁是里面的鸡蛋呢,自然就是torch的Tensor了(换言之就是torch是用tensor计算的,tensor里面的参数都是variable的形式),如果用Variable进行计算,那返回的也是一个同类型的Variable。
Varibale对Tensor进行了封装,包含三个属性:
- data:存储了Tensor,是本体的数据
- grad:保存了data的梯度,本事是个Variable而非Tensor,与data形状一致
- grad_fn:指向Function对象,用于反向传播的梯度计算之用
并且tensor不能反向传播,variable可以反向传播。在Variable计算时,它会逐渐地生成计算图。这个图就是将所有的计算节点都连接起来,最后进行误差反向传递的时候,一次性将所有Variable里面的梯度都计算出来,而tensor就没有这个能力。
import numpy as np
import torch
from torch.autograd import Variable
np_data = np.arange(6).reshape((2, 3))#得到numpy数组
torch_data = torch.from_numpy(np_data)#numpy数组转为tensor张量
tensor2array = torch_data.numpy()#tensor张量转为numpy数组
tensor = torch.FloatTensor([[1,2],[3,4]])#创建Tensor
variable = Variable(tensor, requires_grad=True)#创建variable
v_out = torch.mean(variable*variable)
v_out.backward()
print('v_out:\n', v_out)
'''
v_out:
tensor(7.5000, grad_fn=<MeanBackward0>)
'''
print('variable.grad:\n',variable.grad)
'''
variable.grad:
tensor([[0.5000, 1.0000],
[1.5000, 2.0000]])
'''
print(variable.data)
'''
variable.data:
tensor([[1., 2.],
[3., 4.]])
'''
print('variable.grad_fn:\n', variable.grad_fn)
'''
variable.grad_fn:
None
'''
Pytorch与Numpy类似,具有很多操作方法,详见:https://pytorch.org/docs/stable/torch.html
backward()的理解:
2、实例1:利用pytorch搭建神经网络用于回归或者分类
2.1导入库与数据
主要导入torch库,导入的数据类型应该是tensor,详见实例1代码。
2.2搭建多层神经网络
搭建多层神经网络有常用方法,将神经网络层和激活函数分别写,也可以利用sequential快速搭建神经网络,按照“输入——输出”次序,将神经网络的隐藏层和激活函数一行行写出,笔者推荐快速搭建法便于理解和使用。下面的代码是通过两种方法搭建一个三层神经网络,