首页 文章

关于torch.nn.CrossEntropyLoss参数形状

提问于
浏览
1

我正在学习pytorch,并将基于tensorflow(https://github.com/matthewearl/deep-anprhttp://matthewearl.github.io/2016/05/06/cnn-anpr/)的anpr项目作为练习,将其移植到pytorch平台 .

有一个问题,我使用nn.CrossEntropyLoss()作为损失函数:criterion = nn.CrossEntropyLoss()

模型的output.data是:

  • 1.00000e-02 *

  • 2.5552 2.7582 2.5368 ... 5.6184 1.2288 -0.0076

  • 0.7033 1.3167 -1.0966 ... 4.7249 1.3217 1.8367

  • 0.7592 1.4777 1.8095 ... 0.8733 1.2417 1.1521

  • 0.1040 -0.7054 -3.4862 ... 4.7703 2.9595 1.4263

  • [大小为4x253的torch.FloatTensor]

和targets.data是:

  • 1 0 0 ... 0 0 0

  • 1 0 0 ... 0 0 0

  • 1 0 0 ... 0 0 0

  • 1 0 0 ... 0 0 0

  • [大小为4x253的torch.DoubleTensor]

当我打电话:损失=标准(输出,目标)

发生错误,信息是:TypeError:FloatClassNLLCriterion_updateOutput接收到无效的参数组合 - got(int,torch.FloatTensor, torch.DoubleTensor ,torch.FloatTensor,bool,NoneType,torch.FloatTensor),但是期望(int state,torch.FloatTensor输入, torch.LongTensor target,torch.FloatTensor输出,bool sizeAverage,[torch.FloatTensor weight or None],torch.FloatTensor total_weight)

'expect torch.LongTensor'......'得到了火炬.DoubleTensor',但如果我将目标转换为LongTensor:torch.LongTensor(numpy.array(targets.data.numpy(),numpy.long))

call loss = criterion(输出,目标),错误是:

RuntimeError:/data/users/soumith/miniconda2/conda-bld/pytorch-0.1.10_1488752595704/work/torch/lib/THNN/generic/ClassNLLCriterion.c:20不支持多目标

我的最后一个练习是mnist,来自pytorch的一个例子,我做了一点修改,batch_size是4,丢失函数:loss = F.nll_loss(输出,标签)outputs.data:

  • -2.3220 -2.1229 -2.3395 -2.3391 -2.5270 -2.3269 -2.1055 -2.2321 -2.4943 -2.2996

-2.3653 -2.2034 -2.4437 -2.2708 -2.5114 -2.3286 -2.1921 -2.1771 -2.3343 -2.2533

-2.2809 -2.2119 -2.3872 -2.2190 -2.4610 -2.2946 -2.2053 -2.3192 -2.3674 -2.3100

-2.3715 -2.1455 -2.4199 -2.4177 -2.4565 -2.2812 -2.2467 -2.1144 -2.3321 -2.3009

[大小为4x10的火炬.FloatTensor]

labels.data:

  • 8

  • 6

  • 0

  • 1

  • [torch.LongTensor 4号]

对于输入图像,标签必须是单个元素,在上面的示例中,有253个数字,而在“mnist”中,只有一个数字,输出的形状与标签不同 .

我查看tensorflow手册,tf.nn.softmax_cross_entropy_with_logits,'Logits和标签必须具有相同的形状[batch_size,num_classes]和相同的dtype(float32或float64) .

pytorch在张量流中是否支持相同的功能?

很多人

2 回答

  • 3

    您可以将您拥有的目标转换为分类表示 . 在您提供的示例中,如果类为0,则为1 0 0 0 .. 0,0 1 0 0 ...如果类为1,0 0 1 0 0 0 ...如果类为2我能想到的一个快速方法是首先将目标Tensor转换为numpy数组,然后将其从一个hot转换为一个分类数组,然后将其转换回pytorch Tensor . 像这样的东西:

    targetnp=targets.numpy()
    idxs=np.where(targetnp>0)[1]
    new_targets=torch.LongTensor(idxs)
    loss=criterion(output,new_targets)
    
  • 1

    CrossEntropyLoss 相当于 tf.nn.softmax_cross_entropy_with_logits . CrossEntropyLoss 的输入是形状[batch_size]的分类向量 . 使用 .view() 更改张量形状 .

    labels = labels.view(-1) output = output.view(labels.size(0), -1) loss = criterion(output, loss)

    调用 .view(x, y, -1) 会导致张量使用剩余的数据点来填充 -1 维度,如果没有足够的数量,则会导致错误

    labels.size(0) 给出 label 张量的第0维的大小

    Additional

    要在张量类型之间进行转换,可以在张量上调用类型,例如'labels = labels.long()`

    Second Additional

    如果从像 output.data 这样的变量中解压缩数据,那么你将失去该输出的渐变,并且在时机成熟时无法进行反向提升

相关问题