def test_batch(model_input, labels, model, loss_fn=None):
    """Test the model on `num_steps` batches.

    Args:
        model_input: list of tuples containing input to model
        labels: list of tuples containing labels corresponding to model input
        model: (torch.nn.Module) the neural network
        loss_fn: a function that takes batch_output and batch_labels and computes the loss for the batch

    Returns:
        metrics: dictionary containing metrics if loss_fn given, else returns empty dictionary
    """

    # set model to evaluating mode
    model.eval()

    # compute model output and loss
    model_out = model(*zip(*model_input))

    if loss_fn:
        loss, metrics = loss_fn(*model_out, *zip(*labels))
        return metrics
    else:
        return {}