一、nn.Embedding.weight
初始化分布
nn.Embedding.weight隨機初始化方式是標准正態分布 ,即均值$\mu=0$,方差$\sigma=1$的正態分布。
論據1——查看源代碼
## class Embedding具體實現(在此只展示部分代碼) import torch from torch.nn.parameter import Parameter from .module import Module from .. import functional as F class Embedding(Module): def __init__(self, num_embeddings, embedding_dim, padding_idx=None, max_norm=None, norm_type=2, scale_grad_by_freq=False, sparse=False, _weight=None): if _weight is None: self.weight = Parameter(torch.Tensor(num_embeddings, embedding_dim)) self.reset_parameters() else: assert list(_weight.shape) == [num_embeddings, embedding_dim], \ 'Shape of weight does not match num_embeddings and embedding_dim' self.weight = Parameter(_weight) def reset_parameters(self): self.weight.data.normal_(0, 1) if self.padding_idx is not None: self.weight.data[self.padding_idx].fill_(0)
Embedding
這個類有個屬性weight
,它是torch.nn.parameter.Parameter
類型的,作用就是存儲真正的word embeddings。如果不給weight
賦值,Embedding
類會自動給他初始化,看上述代碼第6~8行,如果屬性weight
沒有手動賦值,則會定義一個torch.nn.parameter.Parameter
對象,然后對該對象進行reset_parameters()
,看第21行,對self.weight
先轉為Tensor
在對其進行normal_(0, 1)
(調整為$N(0, 1)$正態分布)。所以nn.Embeddig.weight
默認初始化方式就是N(0, 1)分布,即均值$\mu=0$,方差$\sigma=1$的標准正態分布。
論據2——簡單驗證nn.Embeddig.weight
的分布
下面將做的是驗證nn.Embeddig.weight
某一行詞向量的均值和方差,以便驗證是否為標准正態分布。
注意:驗證一行數字的均值為0,方差為1,顯然不能說明該分布就是標准正態分布,只能是其必要條件,而不是充分條件,要想真正檢測這行數字是不是正態分布,在概率論上有專門的較為復雜的方法,請查看概率論之假設檢驗。
import torch.nn as nn # dim越大,均值、方差越接近0和1 dim = 800000 # 定義了一個(5, dim)的二維embdding # 對於NLP來說,相當於是5個詞,每個詞的詞向量維數是dim # 每個詞向量初始化為正態分布 N(0,1)(待驗證) embd = nn.Embedding(5, dim) # type(embd.weight) is Parameter # type(embd.weight.data) is Tensor # embd.weight.data[0]是指(5, dim)的word embeddings中取第1個詞的詞向量,是dim維行向量 weight = embd.weight.data[0].numpy() print("weight: {}".format(weight)) weight_sum = 0 for w in weight: weight_sum += w mean = weight_sum / dim print("均值: {}".format(mean)) square_sum = 0 for w in weight: square_sum += (mean - w) ** 2 print("方差: {}".format(square_sum / dim))
代碼輸出:
weight: [-0.65507996 0.11627434 -1.6705967 ... 0.78397447 ... -0.13477565]
均值: 0.0006973597864689242
方差: 1.0019535550544454
可見,均值接近0,方差接近1,從這里也可以反映出nn.Embeddig.weight
是標准正態分布$N(0, 1)$。
二、torch.Tensor
、torch.tensor
、torch.randn
初始化分布
1、torch.rand
返回$[0,1)$上的均勻分布(uniform distribution)。
2、torch.randn
返回$N(0, 1)$,即標准正態分布(standard normal distribution)。
3、torch.Tensor
torch.Tensor
是Tensor class,torch.Tensor(2, 3)
是調用Tensor的構造函數,構造了$2\times3$矩陣,但是沒有分配空間,未初始化。
不推薦使用torch.Tensor
創建Tensor,應使用torch.tenstor
、torch.ones
、torch.zeros
、torch.rand
、torch.randn
等,原因:
t = torch.Tensor(2,3)
# 容易出現下述錯誤,因為t中的值取決當前內存中的隨機值
# 如果當前內存中隨機值特別大會溢出
RuntimeError: Overflow when unpacking long
