Repository: ivy-llc/ivy

Issue:
nll_loss



Discussion:

Resolving patch:
diff --git a/ivy/functional/frontends/paddle/nn/functional/loss.py b/ivy/functional/frontends/paddle/nn/functional/loss.py
--- a/ivy/functional/frontends/paddle/nn/functional/loss.py
+++ b/ivy/functional/frontends/paddle/nn/functional/loss.py
@@ -282,3 +282,36 @@ def triplet_margin_loss(
 
     loss = reduction(loss).astype(input.dtype)
     return loss
+
+
+@with_supported_dtypes({"2.5.1 and below": ("float32", "float64")}, "paddle")
+@to_ivy_arrays_and_back
+def nll_loss(
+    input,
+    label,
+    weight=None,
+    ignore_index=-100,
+    reduction="mean",
+):
+    """Refer
+    https://pytorch.org/docs/stable/generated/torch.nn.NLLLoss.html#torch.nn.NLLLoss for
+    more on NLL(Negative log likelihood) Loss."""
+    if weight is None:
+        weight = ivy.ones(ivy.shape(input[0]))
+    input = ivy.log(input)
+    loss = ivy.zeros(ivy.shape(label))
+    den = 0
+    for i in range(0, ivy.shape(loss)[0]):
+        den = den + weight[label[i]]
+        loss[i] = -weight[label[i]] * input[i][label[i]]
+    output = 0.0
+    if reduction == "sum":
+        output = ivy.sum(loss)
+        if ignore_index >= 0 and ignore_index < ivy.shape(input)[1]:
+            output = output - loss[ignore_index]
+        return output
+    num = ivy.sum(loss)
+    output = num / den
+    if ignore_index >= 0 and ignore_index < ivy.shape(input)[1]:
+        output = output - loss[ignore_index] / den
+    return output


Test patch:
diff --git a/ivy_tests/test_ivy/test_frontends/test_paddle/test_nn/test_functional/test_loss.py b/ivy_tests/test_ivy/test_frontends/test_paddle/test_nn/test_functional/test_loss.py
--- a/ivy_tests/test_ivy/test_frontends/test_paddle/test_nn/test_functional/test_loss.py
+++ b/ivy_tests/test_ivy/test_frontends/test_paddle/test_nn/test_functional/test_loss.py
@@ -440,3 +440,54 @@ def test_paddle_triplet_margin_loss(
         swap=swap,
         reduction=reduction,
     )
+
+
+@handle_frontend_test(    
+    fn_tree="paddle.nn.functional.nll_loss",
+    dtype_and_x=helpers.dtype_and_values(
+        available_dtypes=helpers.get_dtypes("float"),
+        num_arrays=2,
+        shared_dtype=True,
+        min_num_dims=1,
+        max_num_dims=2,
+    ),
+    dtype_and_weight=helpers.dtype_and_values(
+        available_dtypes=helpers.get_dtypes("float"),
+        num_arrays=1,
+        max_num_dims=1,
+    ),
+    ignore_index=st.integers(
+        min_value=-100,
+    ),
+    reduction=st.sampled_from(["mean", "sum", "none"]),
+)
+def test_paddle_nll_loss(
+    dtype_and_x,
+    dtype_and_weight,
+    ignore_index,
+    reduction,
+    on_device,
+    fn_tree,
+    frontend,
+    test_flags,
+    backend_fw,
+):
+    x_dtype, x = dtype_and_x
+    weight_dtype, weight = dtype_and_weight
+    helpers.test_frontend_function(
+        input_dtypes=[
+            x_dtype[0],
+            x_dtype[1],
+            weight_dtype[0],
+        ],
+        backend_to_test=backend_fw,
+        frontend=frontend,
+        test_flags=test_flags,
+        fn_tree=fn_tree,
+        on_device=on_device,
+        input=x[0],
+        label=x[1],
+        weight=weight[0],
+        ignore_index=ignore_index,
+        reduction=reduction,
+    )