[人工智能]Pytorch基礎

PyTorch基礎

摘抄自《深度學習之Pytorch》。python

Tensor(張量)

PyTorch裏面處理的最基本的操做對象就是Tensor,表示的是一個多維矩陣,好比零維矩陣就是一個點,一維就是向量,二維就是通常的矩陣,多維就至關於一個多維數組,這和numpy是對應,並且PyTorch的Tensor能夠和numpy的ndarray相互轉換,惟一不一樣的是PyTorch能夠在GPU上運行,而numpy的ndarray只能在CPU上運行。算法

經常使用的不一樣數據類型的Tensor有32位浮點型torch.FloatTensor64位浮點型torch.DoubleTensor16位整型torch.ShortTensor32位整型torch.IntTensor64位浮點型torch.LongTensor。torch.Tensor默認的是torch.FloatTensor數據類型。數組

Variable(變量)

Variable,變量,這個概念在numpy中是沒有,是神經網絡計算圖裏特有的一個概念,就是Variable提供了自動求導的功能。網絡

Variable和Tensor本質上沒有區別,不過Variable會被放入一個計算圖中,而後進行前向傳播、反向傳播、自動求導。多線程

首先Variable是在torch.autograd.Variable中,要將tensor變成Variable也很是簡單,好比想讓一個tensor a變成Variable,只需Variable(a)便可。機器學習

Variable有三個比較重要的組成屬性:data,grad和grad_fn。經過data能夠取出Variable裏面的tensor數值;grad_fn表示的是獲得這個Variable的操做,好比經過加減仍是乘除獲得的;grad是這個Variable的反向傳播梯度。函數

Dataset(數據集)

在處理任何機器學習問題以前都須要數據讀取,並進行預處理。PyTorch提供了不少工具使得數據的讀取和預處理變得很容易。工具

torch.utils.data.Dataset是表明這一數據的抽象類。你能夠本身定義你的數據類,繼承和重寫這個抽象類,很是簡單,只須要定義__len__和__getitem__這個兩個函數:學習

class myDataset(Dataset):
    def __init__(self,csv_file,txt_file,root_dir,other_file):
        self.csv_data = pd.read_csv(csv_file)
        with open(txt_file,'r') as f:
            data_list = f.readlines()
        self.txt_data = data_list
        self.root_dir = root_dir

    def __len__(self):
        return len(self.csv_data)

    def __gettime__(self,idx):
        data = (self.csv_data[idx],self.txt_data[idx])
        return data

經過上面的方式,能夠定義咱們須要的數據類,能夠同迭代的方式來獲取每個數據,但這樣很難實現缺batch,shuffle或者是多線程去讀取數據,因此PyTorch中提供了一個簡單的辦法來作這個事情,經過torch.utils.data.DataLoader來定義一個新的迭代器,以下:優化

dataiter = DataLoader(myDataset,batch_size=32,shuffle=True,collate_fn=defaulf_collate)

其中的參數都很清楚,只有collate_fn是標識如何去樣本的,咱們能夠定義本身的函數來準確地實現想要的功能,默認的函數在通常狀況下都是可使用的。

nn.Module(模組)

在PyTorch裏面編寫神經網絡,全部的層結構和損失函數都來自於torch.nn,全部的模型構建都是從這個基類nn.Module繼承的,因而有了下面的這個模板。

class net_name(nn.Module):
    def __init__(self,other_arguments):
        super(net_name,self).__init__()
        self.conv1 = nn.Conv2d(in_channels,out_channels,kernel_size)
        # other network layer

    def forward(self,x):
        x = self.conv1(x)
        return x

這樣就創建一個計算圖,而且這個結構能夠複用屢次,每次調用就至關於用該計算圖定義的相同參數作一次前向傳播,得益於PyTorch的自動求導功能,因此咱們不須要本身編寫反向傳播。

定義完模型以後,咱們須要經過nn這個包來定義損失函數。常見的損失函數都已經定義在了nn中,好比均方偏差、多分類的交叉熵以及二分類的交叉熵等等,調用這些已經定義好的的損失函數也很簡單:

criterion = nn.CrossEntropyLoss()]
loss = criterion(output,target)

這樣就能求得咱們的輸出和真實目標之間的損失函數了。

torch.optim(優化)

在機器學習或者深度學習中,咱們須要經過修改參數使得損失函數最小化(或最大化),優化算法就是一種調整模型參數更新的策略。

優化算法分爲兩大類:

  1. 一階優化算法

這種算法使用各個參數的梯度值來更新參數,最經常使用的一階優化算法是梯度降低。所謂的梯度就是導數的多變量表達式,函數的梯度造成了一個向量場,同時也是一個方向,這個方向上方向導數最大,且等於梯度。梯度降低的功能是經過尋找最小值,控制方差,更新模型參數,最終使模型收斂,網絡的參數更新公式以下:

$\theta = \theta - \eta \times\frac{\sigma J(\theta)}{\sigma_\theta}$

其中$\eta$是學習率,$\frac{\sigma J(\theta)}{\sigma_\theta}$是函數的梯度。這是深度學習裏最經常使用的優化方法。

  1. 二階優化算法

二階優化算法是用來二階導數(也叫作Hessian方法)來最小化或最大化損失函數,主要基於牛頓法,但因爲二階導數的計算成本很高,因此這種方法並無普遍使用。torch.optim是一個實現各類優化算法的包,大多數常見的算法都能到直接經過這個包來調用,好比隨機梯度降低,以及添加動量的隨機梯度降低,自適應學習率等。在調用的時候須要優話傳入的參數,這些參數都必須是Variable,而後傳入一些基本的設定,好比學習率和動量等。

模型的保存和加載

在PyTorch中使用torch.save來保存模型的結構和參數,有兩種保存方式:

  1. 保存整個模型的結構信息和參數信息,保存對象是模型model;
  2. 保存模型的參數,保存的對象是模型的狀態model.state_dict()。

能夠按以下方式保存:save的第一個參數是保存對象,第二個參數是保存路徑及名稱:

torch.save(model,'./model.pth')
    torch.save(model.state_dict(),'./model_state.pth')

加載模型有兩種對應於保存模型的方式:

  1. 加載完整的模型結構和參數信息,使用 load_model = torch.load('model.pth'),在網絡較大的時候加載的時間較長,同時存儲空間也比較大;
  2. 加載模型參數信息,須要先導入模型的結構,而後經過 model.load_state_dic(torch.load('model_state.pth'))來導入。