{"record":{"id":"da22709ef6be3c06","repo":"keras-team/keras","slug":"argument-recall-must-be-in-the-range-0-1-rec","errorCode":null,"errorMessage":"Argument `recall` must be in the range [0, 1]. Received: recall={recall}","messagePattern":"Argument `recall` must be in the range \\[0, 1\\]\\. Received: recall=(.+?)","errorType":"exception","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"keras/src/metrics/confusion_metrics.py","lineNumber":937,"sourceCode":"    ...                sample_weight=[2, 2, 2, 1, 1])\n    >>> m.result()\n    0.33333333\n\n    Usage with `compile()` API:\n\n    ```python\n    model.compile(\n        optimizer='sgd',\n        loss='binary_crossentropy',\n        metrics=[keras.metrics.PrecisionAtRecall(recall=0.8)])\n    ```\n    \"\"\"\n\n    def __init__(\n        self, recall, num_thresholds=200, class_id=None, name=None, dtype=None\n    ):\n        if recall < 0 or recall > 1:\n            raise ValueError(\n                \"Argument `recall` must be in the range [0, 1]. \"\n                f\"Received: recall={recall}\"\n            )\n        self.recall = recall\n        self.num_thresholds = num_thresholds\n        super().__init__(\n            value=recall,\n            num_thresholds=num_thresholds,\n            class_id=class_id,\n            name=name,\n            dtype=dtype,\n        )\n\n    def result(self):\n        recalls = ops.divide_no_nan(\n            self.true_positives,\n            ops.add(self.true_positives, self.false_negatives),\n        )","sourceCodeStart":919,"sourceCodeEnd":955,"githubUrl":"https://github.com/keras-team/keras/blob/7a34a03db60bf60042242d6a556fc3be119046a5/keras/src/metrics/confusion_metrics.py#L919-L955","documentation":"Raised by keras.metrics.PrecisionAtRecall's __init__ when the recall target is outside [0, 1]. The metric finds the threshold at which recall reaches the given value, so recall must be a valid probability.","triggerScenarios":"keras.metrics.PrecisionAtRecall(recall=1.1); recall as percentage (80 for 80%); uninitialized config defaulting to -1.","commonSituations":"Config sweeps with -1 sentinels; percent/fraction mix-ups; ported sklearn-style code.","solutions":["Pass recall as a fraction in [0, 1], e.g. 0.8.","Validate sweep/config ranges before constructing the metric.","Convert percentages explicitly: recall_pct / 100.0."],"exampleFix":"# before\nm = keras.metrics.PrecisionAtRecall(recall=80)\n\n# after\nm = keras.metrics.PrecisionAtRecall(recall=0.8)","handlingStrategy":"validation","validationCode":"if not (0.0 <= recall <= 1.0):\n    raise ValueError(f'recall must be in [0,1], got {recall}')","typeGuard":"def is_probability(v) -> bool:\n    return isinstance(v, (int, float)) and 0.0 <= v <= 1.0","tryCatchPattern":null,"preventionTips":["Exclude -1 sentinels from sweeps over probability-like args.","Name config keys with a _frac suffix to signal units."],"tags":["keras","metrics","recall","range-validation"],"backgroundTag":"probability-out-of-range","analyzedSha":"7a34a03db60bf60042242d6a556fc3be119046a5","analyzedAt":"2026-08-25T21:25:25.994Z","schemaVersion":2},"datasetVersion":"2026-08-26T02:17:13.382Z"}