{"record":{"id":"659b0608974ad657","repo":"pandas-dev/pandas","slug":"searchsorted-requires-array-to-be-sorted-which-is-659b06","errorCode":null,"errorMessage":"searchsorted requires array to be sorted, which is impossible with NAs present.","messagePattern":"searchsorted requires array to be sorted, which is impossible with NAs present\\.","errorType":"exception","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"pandas/core/arrays/masked.py","lineNumber":1440,"sourceCode":"\n        Returns\n        -------\n        array of ints or int\n            If value is array-like, array of insertion points.\n            If value is scalar, a single integer.\n\n        See Also\n        --------\n        numpy.searchsorted : Similar method from NumPy.\n\n        Examples\n        --------\n        >>> arr = pd.array([1, 2, 3, 5])\n        >>> arr.searchsorted([4])\n        array([3])\n        \"\"\"\n        if self._hasna:\n            raise ValueError(\n                \"searchsorted requires array to be sorted, which is impossible \"\n                \"with NAs present.\"\n            )\n        if isinstance(value, ExtensionArray):\n            value = value.astype(object)\n        # Base class searchsorted would cast to object, which is *much* slower.\n        return self._data.searchsorted(value, side=side, sorter=sorter)\n\n    def factorize(\n        self,\n        use_na_sentinel: bool = True,\n    ) -> tuple[np.ndarray, ExtensionArray]:\n        \"\"\"\n        Encode the extension array as an enumerated type.\n\n        Parameters\n        ----------\n        use_na_sentinel : bool, default True","sourceCodeStart":1422,"sourceCodeEnd":1458,"githubUrl":"https://github.com/pandas-dev/pandas/blob/3b7651241d4da534b3559b60ef128e1c34f54116/pandas/core/arrays/masked.py#L1422-L1458","documentation":"Raised by BaseMaskedArray.searchsorted when self._hasna is True. searchsorted requires a totally ordered array, but pandas NA has no ordering relative to the other values, so a sorted position for a search cannot be defined reliably; pandas raises instead of returning a misleading index.","triggerScenarios":"Calling arr.searchsorted(value) on a nullable masked ExtensionArray (Int64, Float64) that contains at least one missing value (mask bit set).","commonSituations":"Running bisect-style lookups on a nullable column that still has NAs; using searchsorted on a sorted-but-not-yet-filled Series for index alignment; binary-search optimizations on dirty data.","solutions":["Fill or drop NAs first: arr.dropna().searchsorted(value) or arr.fillna(limit).searchsorted(value).","Use a non-nullable dtype with a sentinel that preserves sort order.","Filter NAs out and keep a separate index map if original positions are needed."],"exampleFix":"// before\narr = pd.array([1, None, 3, 5], dtype='Int64')\narr.searchsorted(4)   # raises\n// after\narr.dropna().searchsorted(4)","handlingStrategy":"validation","validationCode":"if arr._hasna:\n    raise ValueError('Cannot searchsorted with NAs; drop or fill first')\nidx = arr.searchsorted(value)","typeGuard":"def is_searchsortable(arr) -> bool:\n    return not arr._hasna","tryCatchPattern":"try:\n    idx = arr.searchsorted(value)\nexcept ValueError as e:\n    if 'sorted' in str(e) and 'NAs' in str(e):\n        idx = arr.dropna().searchsorted(value)\n    else:\n        raise","preventionTips":["Drop or fill NAs before calling searchsorted.","Maintain a sorted, NA-free view for bisect-style lookups.","Check _hasna at the start of lookup-heavy code paths."],"tags":["pandas","masked-array","searchsorted","na-value","sorting"],"backgroundTag":null,"analyzedSha":"3b7651241d4da534b3559b60ef128e1c34f54116","analyzedAt":"2026-08-11T22:10:44.015Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}