Scale each instance by mask area in L1 loss

L1 loss by default uses reduction=mean and weighs loss on differently sized instances.

But consider the following scenario:
I have a set size for batches and image dimensions, but each image has different masks where only a certain region is of interest.
I think it could be useful to scale each instance’s loss by the area of the region of interest (i.e. number of ones in the mask).

I don’t believe elements which are exactly zero are ignored in L1Loss, are they?

Could something like this work?

# Assume 'input', 'output', 'mask' all are NCHW

output = model(input)
diff = input*mask - output*mask
weighted_diff = mask.sum([1,2,3]) * diff
loss = L1_loss(weighted_diff, torch.zeros_like(weighted_diff))

I am not sure about the use case.
But do you think, the losses from the images with “less mask area” should be weighed higher? If not, the model might get away by ignoring them.
i.e.,

output = model(input)
abs_diff = torch.abs((input - output)*mask).sum([1,2,3])
loss = abs_diff / (mask.sum([1,2,3]) + eps)  # eps ~ 10-6
1 Like

Ah yes you are correct!
I meant scaling it by the inverse scale of the mask which is what I assume you are referring to in the last line of code.

I am curious if there was some torch component or loss function argument that did this “behind the scenes”. I think it might just be better to do it explicitly like you suggested.

I haven’t come across a specific implementation in torch that gives this functionality so far.
You might need to look around in the docs.

1 Like