我更改了标量类型 float 的预期对象,但在 Pytorch 中仍然得到 Long
Posted
技术标签:
【中文标题】我更改了标量类型 float 的预期对象,但在 Pytorch 中仍然得到 Long【英文标题】:I change the expected object of scalar type float but still got Long in Pytorch 【发布时间】:2019-09-04 01:10:22 【问题描述】:做二元类分类。我使用二元交叉熵作为损失函数(nn.BCEloss()),最后一层的单位是1。
在将 (input, target) 放入损失函数之前,我将 target 从 Long 转换为 float。只有DataLoader的最后一步是报错信息,报错信息如下。
"RuntimeError: Expected object of scalar type Float but got scalar type Long for argument #2 'target'"
代码中定义了DataLoader(如果批量大小不匹配,我会丢弃最后一批),我不确定是否与错误相关。
我尝试打印目标和输入的类型(神经网络的输出),两个变量的类型都是浮点数。我把“类型结果”和代码放在下面。
trainloader = torch.utils.data.DataLoader(trainset, batch_size=BATCH_SIZE,
shuffle=True, drop_last=True)
loss_func = nn.BCELoss()
# training
for epoch in range(EPOCH):
test_loss = 0
train_loss = 0
for step, (b_x, b_y) in enumerate(trainloader): # gives batch data
b_x = b_x.view(-1, TIME_STEP, 1) # reshape x to (batch, time_step, input_size)
print("step: ", step)
b_x = b_x.to(device)
print("BEFORE|b_y type: ",b_y.type())
b_y = b_y.to(device, dtype=torch.float)
print("AFTER|b_y type: ",b_y.type())
output = rnn(b_x) # rnn output
print("output type:", output.type())
loss = loss_func(output, b_y) # !!!error occurs when trainloader enumerate the final step!!!
train_loss = train_loss + loss
optimizer.zero_grad()
loss.backward()
optimizer.step()
#### type result and the error message####
...
step: 6
BEFORE|b_y type: torch.LongTensor
AFTER|b_y type: torch.cuda.FloatTensor
output type: torch.cuda.FloatTensor
---------------------------------------------------------------------------
RuntimeError Traceback (most recent call last)
<ipython-input-18-e028fcb6b840> in <module>
30 b_y = b_y.to(device)
31 output = rnn(b_x)
---> 32 loss = loss_func(output, b_y)
33 test_loss = test_loss + loss
34 rnn.train()
~/venvs/tf1.12/lib/python3.5/site-packages/torch/nn/modules/module.py in __call__(self, *input, **kwargs)
487 result = self._slow_forward(*input, **kwargs)
488 else:
--> 489 result = self.forward(*input, **kwargs)
490 for hook in self._forward_hooks.values():
491 hook_result = hook(self, input, result)
~/venvs/tf1.12/lib/python3.5/site-packages/torch/nn/modules/loss.py in forward(self, input, target)
502 @weak_script_method
503 def forward(self, input, target):
--> 504 return F.binary_cross_entropy(input, target, weight=self.weight, reduction=self.reduction)
505
506
~/venvs/tf1.12/lib/python3.5/site-packages/torch/nn/functional.py in binary_cross_entropy(input, target, weight, size_average, reduce, reduction)
2025
2026 return torch._C._nn.binary_cross_entropy(
-> 2027 input, target, weight, reduction_enum)
2028
2029
RuntimeError: Expected object of scalar type Float but got scalar type Long for argument #2 'target'
【问题讨论】:
【参考方案1】:看起来类型正在正确更改,因为您声明在打印类型和从 Pytorch 时观察到更改:
返回带有指定设备的
Tensor
和(可选)dtype
。如果 dtype 为 None 它被推断为self.dtype
。当non_blocking
, 如果可能,尝试相对于主机进行异步转换, 例如,将带有固定内存的 CPU 张量转换为 CUDA 张量。 设置副本时,即使张量已经创建,也会创建一个新张量 匹配所需的转换。
和其他方法,如
b_y = b_y.to(device).float()
不应该有明显的不同,因为.float()
等同于.to(..., torch.float32)
。而.float
等价于.float32
。您能否在引发错误之前验证 b_y
的类型并编辑问题? (我会对此发表评论 - 但我想添加更多细节。提供时我会尽力提供帮助)
【讨论】:
感谢您的帮助!我打印这两个变量的类型(输出,b_y)。这是代码和结果。BEFORE|b_y type: torch.LongTensor AFTER|b_y type: torch.cuda.FloatTensor output type: torch.cuda.FloatTensor
以上是关于我更改了标量类型 float 的预期对象,但在 Pytorch 中仍然得到 Long的主要内容,如果未能解决你的问题,请参考以下文章
pytorch RuntimeError: 标量类型 Double 的预期对象,但得到标量类型 Float
RuntimeError: 标量类型 Long 的预期对象,但参数 #2 'mat2' 的标量类型 Float 如何解决?
RuntimeError:预期的标量类型 Long 但发现 Float
Pytorch RuntimeError:预期的标量类型 Float 但找到了字节
RuntimeError:预期的标量类型 Double 但发现 Float
通过 DataLoader (PyTorch) 迭代:RuntimeError: 标量类型 unsigned char 的预期对象但序列元素 9 的标量类型浮点数