{"record":{"id":"fec7d1b40b32266e","repo":"pola-rs/polars","slug":"category-index-out-of-range-key","errorCode":null,"errorMessage":"category index out of range: {key}","messagePattern":"category index out of range: (.+?)","errorType":"exception","errorClass":"IndexError","httpStatus":null,"severity":"error","filePath":"py-polars/src/polars/datatypes/classes.py","lineNumber":851,"sourceCode":"        elif phys == \"u32\":\n            return pldt.UInt32\n        else:\n            msg = \"unknown physical dtype\"\n            raise RuntimeError(msg)\n\n    def is_global(self) -> bool:\n        \"\"\"Returns whether this refers to the global categories.\"\"\"\n        return self._categories.is_global()\n\n    def __getitem__(self, key: str | int) -> str | int:\n        if isinstance(key, str):\n            if (cat := self._categories.get_cat(key)) is None:\n                raise KeyError(key)\n            return cat\n        elif isinstance(key, int):\n            if (s := self._categories.cat_to_str(key)) is None:\n                msg = f\"category index out of range: {key}\"\n                raise IndexError(msg)\n            return s\n        else:\n            msg = f\"invalid key type {type(key)}; expected str or int\"\n            raise TypeError(msg)\n\n    def __contains__(self, item: str | int) -> bool:\n        if isinstance(item, str):\n            return self._categories.get_cat(item) is not None\n        elif isinstance(item, int):\n            return self._categories.cat_to_str(item) is not None\n        else:\n            return False\n\n    def __iter__(self) -> Iterator[str | None]:\n        for i in range(self._categories.num_cats_upper_bound()):\n            yield self._categories.cat_to_str(i)\n\n    def to_series(self) -> Series:","sourceCodeStart":833,"sourceCodeEnd":869,"githubUrl":"https://github.com/pola-rs/polars/blob/68506541d2de983056c9eb244e1ea05fab377dfc/py-polars/src/polars/datatypes/classes.py#L833-L869","documentation":"IndexError raised by a Categorical's CategoriesMapping.__getitem__ when an integer index is outside the category table (negative or >= number of categories). The mapping only stores as many codes as distinct categories, so any out-of-range physical code has no string to return.","triggerScenarios":"categories[999] on a categorical with fewer categories; using a physical code obtained from a different (larger) categorical vocabulary; negative indices below the mapping's range.","commonSituations":"Debugging by dumping category codes; joining/concatenating categoricals with mismatched string caches or global category spaces; stale indices saved before a categorical was rebuilt.","solutions":["Validate the index: 0 <= i < len(categories) before indexing","Use cat_to_str(key) which returns None for invalid codes","When combining categoricals, cast to String or use Categorical('lexical') / union so codes share one vocabulary"],"exampleFix":"# before\nlabel = dtype.categories[1234]\n# after\nlabel = dtype.categories.cat_to_str(1234)\nif label is None:\n    ...  # index out of range","handlingStrategy":"validation","validationCode":"if not (0 <= idx < dtype.categories.len()):\n    raise IndexError(f'bad category code {idx}')","typeGuard":"def valid_code(dtype: pl.DataType, idx: int) -> bool:\n    return dtype.categories.cat_to_str(idx) is not None","tryCatchPattern":"try:\n    label = dtype.categories[i]\nexcept IndexError:\n    label = None  # stale/foreign physical code","preventionTips":["Never persist physical codes across categorical rebuilds","Use cat_to_str for safe lookups","Rebuild or union categories when combining sources"],"tags":["python","polars","categorical","index-error","categories"],"backgroundTag":"index-out-of-range","analyzedSha":"68506541d2de983056c9eb244e1ea05fab377dfc","analyzedAt":"2026-08-28T18:02:35.179Z","contentChangedAt":"2026-08-28T18:02:35.179Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}