Unverified Commit 9cae1562 authored by YosuaMichael's avatar YosuaMichael Committed by GitHub
Browse files

Add test for giou_loss (#5792)



* Add test for giou_loss

* Use standard assert for integer comparison
Co-authored-by: default avatarPhilip Meier <github.pmeier@posteo.de>

* Fix ufmt format and add log after assert
Co-authored-by: default avatarPhilip Meier <github.pmeier@posteo.de>
parent 467b841a
......@@ -1569,5 +1569,59 @@ class TestFocalLoss:
torch.testing.assert_close(focal_loss, scripted_focal_loss, rtol=tol, atol=tol)
class TestGeneralizedBoxIouLoss:
# We refer to original test: https://github.com/facebookresearch/fvcore/blob/main/tests/test_giou_loss.py
@pytest.mark.parametrize("device", cpu_and_gpu())
@pytest.mark.parametrize("dtype", [torch.float32, torch.half])
def test_giou_loss(self, dtype, device) -> None:
box1 = torch.tensor([-1, -1, 1, 1], dtype=dtype, device=device)
box2 = torch.tensor([0, 0, 1, 1], dtype=dtype, device=device)
box3 = torch.tensor([0, 1, 1, 2], dtype=dtype, device=device)
box4 = torch.tensor([1, 1, 2, 2], dtype=dtype, device=device)
box1s = torch.stack([box2, box2], dim=0)
box2s = torch.stack([box3, box4], dim=0)
def assert_giou_loss(box1, box2, expected_loss, reduction="none"):
tol = 1e-3 if dtype is torch.half else 1e-5
computed_loss = ops.generalized_box_iou_loss(box1, box2, reduction=reduction)
expected_loss = torch.tensor(expected_loss, device=device)
torch.testing.assert_close(computed_loss, expected_loss, rtol=tol, atol=tol)
# Identical boxes should have loss of 0
assert_giou_loss(box1, box1, 0.0)
# quarter size box inside other box = IoU of 0.25
assert_giou_loss(box1, box2, 0.75)
# Two side by side boxes, area=union
# IoU=0 and GIoU=0 (loss 1.0)
assert_giou_loss(box2, box3, 1.0)
# Two diagonally adjacent boxes, area=2*union
# IoU=0 and GIoU=-0.5 (loss 1.5)
assert_giou_loss(box2, box4, 1.5)
# Test batched loss and reductions
assert_giou_loss(box1s, box2s, 2.5, reduction="sum")
assert_giou_loss(box1s, box2s, 1.25, reduction="mean")
@pytest.mark.parametrize("device", cpu_and_gpu())
@pytest.mark.parametrize("dtype", [torch.float32, torch.half])
def test_empty_inputs(self, dtype, device) -> None:
box1 = torch.randn([0, 4], dtype=dtype).requires_grad_()
box2 = torch.randn([0, 4], dtype=dtype).requires_grad_()
loss = ops.generalized_box_iou_loss(box1, box2, reduction="mean")
loss.backward()
tol = 1e-3 if dtype is torch.half else 1e-5
torch.testing.assert_close(loss, torch.tensor(0.0), rtol=tol, atol=tol)
assert box1.grad is not None, "box1.grad should not be None after backward is called"
assert box2.grad is not None, "box2.grad should not be None after backward is called"
loss = ops.generalized_box_iou_loss(box1, box2, reduction="none")
assert loss.numel() == 0, "giou_loss for two empty box should be empty"
if __name__ == "__main__":
pytest.main([__file__])
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment