如何在NLP上使用pytorch实现丢失?
我正在用Pytork研究NLP,它只是一个简单的玩具项目(只是生成文本)。当我在网上引用一些示例代码时,遇到了一个我无法理解的问题 以下是代码(一些代码已被省略,尚未完成):如何在NLP上使用pytorch实现丢失?,nlp,lstm,dimension,loss,cross-entropy,Nlp,Lstm,Dimension,Loss,Cross Entropy,我正在用Pytork研究NLP,它只是一个简单的玩具项目(只是生成文本)。当我在网上引用一些示例代码时,遇到了一个我无法理解的问题 以下是代码(一些代码已被省略,尚未完成): LSTM模型(utils.py) main.py 所以,我不明白的是,为什么张量logits(main.py末尾的代码)必须被转置 登录的形状和标签为: logits : torch.Size([16, 19, 10002]) # [batch_size, setence_length, vocab_size] label
logits
(main.py末尾的代码)必须被转置
登录的形状和标签为:
logits : torch.Size([16, 19, 10002]) # [batch_size, setence_length, vocab_size]
label : torch.Size([16, 19]) # [batch_size, setence_length]
在我看来,要用交叉熵来计算损失,标签的形状和数据的形状必须是相同的维度,但事实并非如此。(标签形状:[批次大小、设置长度]->[批次大小、设置长度、声音大小])
我怎么能理解呢?为什么它会起作用
我在下面的网站上引用了!
:https://machinetalk.org/2019/02/08/text-generation-with-pytorch/
nn.CrossEntropyLoss()
不接受一个热向量。相反,它接受类值。因此,您的登录和目标将不具有相同的维度。Logits必须是维度(num\u示例,vocab\u大小)
,但标签只需包含真实类的索引,这样它的形状将是(num\u示例)
而不是(num\u示例,vocab\u大小)
。只有在输入一个热编码向量时,才需要该形状
至于为什么需要转置logits向量,nn.CrossEntropyLoss()
希望logits向量的维度为(批次大小、数量类、损失大小)
,其中损失大小是每个批次中的令牌数
if __name__=="__main__":
""" 데이터 불러오기.
"""
corpus, word2id, id2word, weight = load_data()
corpus = torch.LongTensor(corpus)
""" 하이퍼 파라미터.
"""
# 훈련
epochs = 10
learning_rate = 0.003
batch_size = 16
hidden_size = 32 # lstm hidden 값 차원수
gradients_norm=5 # 기울기 클리핑.
# 문장
seq_size=len(corpus[0]) # 문장 1개 길이.
embedding_size=len(weight[0]) # 임베딩 벡터 사이즈.
vocab_size = len(word2id)
# 테스트
# initial_words=['I', 'am']
predict_top_k=5
checkpoint_path='./checkpoint'
device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')
print('# corpus size : {} / vocab_size : {}'.format(len(corpus), vocab_size))
print('# batch size : {} / num of cell : {}'.format(batch_size, hidden_size))
print("# 디바이스 : ", device)
print('-'*30+"데이터 불러오기 및 하이퍼 파라미터 설정 분할 완료.")
""" data/label 분할
"""
c = corpus.numpy() # corpus가 Tensor 형태이므로 정상적인 slicing을 위해 numpy 형태로 바꾸어준다.
data, label = make_data_label(c)
dataset = CommentDataset(data, label)
dataloader = DataLoader(dataset, batch_size=batch_size, shuffle=True)
print('-'*30 + "Data Loader 준비 완료.")
""" Model 정의 및 생성.
"""
net = RNNModule(vocab_size, seq_size,
embedding_size, hidden_size)
net = net.to(device)
loss_f = nn.CrossEntropyLoss()
optimizer = torch.optim.Adam(net.parameters(), lr=learning_rate)
for batch_idx, sample in enumerate(dataloader) :
data, label = sample
data = data.to(device)
label = label.to(device)
state_h, state_c = net.zero_state(batch_size) # initial h, c
state_h = state_h.to(device)
state_c = state_c.to(device)
logits, (state_h, state_c) = net.forward(data, (state_h, state_c))
print(logits.transpose(1, 2).size())
print(label.size())
loss = loss_f(logits.transpose(1, 2), label)
loss.backward()
optimizer.step()
break
logits : torch.Size([16, 19, 10002]) # [batch_size, setence_length, vocab_size]
label : torch.Size([16, 19]) # [batch_size, setence_length]