pandas-dev/pandas · error · TypeError

pd.api.extensions.take requires a numpy.ndarray, ExtensionAr

Error message

pd.api.extensions.take requires a numpy.ndarray, ExtensionArray, Index, Series, or NumpyExtensionArray got {type(arr).__name__}.

What it means

Raised by pd.api.extensions.take when the source array is not one of the supported types (numpy.ndarray, ExtensionArray, Index, Series, NumpyExtensionArray). The take routine needs array-like indexing semantics; a plain Python list, dict, or scalar cannot be safely indexed.

Source

Thrown at pandas/core/algorithms.py:1374

    >>> pd.api.extensions.take(np.array([10, 20, 30]), [0, 0, -1])
    array([10, 10, 30])

    Setting ``allow_fill=True`` will place `fill_value` in those positions.

    >>> pd.api.extensions.take(np.array([10, 20, 30]), [0, 0, -1], allow_fill=True)
    array([10., 10., nan])

    >>> pd.api.extensions.take(
    ...     np.array([10, 20, 30]), [0, 0, -1], allow_fill=True, fill_value=-10
    ... )
    array([ 10,  10, -10])
    """
    if not isinstance(
        arr,
        (np.ndarray, ABCExtensionArray, ABCIndex, ABCSeries, ABCNumpyExtensionArray),
    ):
        # GH#52981
        raise TypeError(
            "pd.api.extensions.take requires a numpy.ndarray, ExtensionArray, "
            f"Index, Series, or NumpyExtensionArray got {type(arr).__name__}."
        )

    indices = ensure_platform_int(indices)

    if allow_fill:
        # Pandas style, -1 means NA
        validate_indices(indices, arr.shape[axis])
        # error: Argument 1 to "take_nd" has incompatible type
        # "ndarray[Any, Any] | ExtensionArray | Index | Series"; expected
        # "ndarray[Any, Any]"
        result = take_nd(
            arr,  # type: ignore[arg-type]
            indices,
            axis=axis,
            allow_fill=True,
            fill_value=fill_value,

View on GitHub (pinned to 71959b8cb9)

Solutions

  1. Convert the input to np.ndarray or a pandas Series/Index first.
  2. Use np.take for plain lists, or pd.api.extensions.take(np.asarray(lst), idx).
  3. Validate the type before calling take.

Example fix

# before
pd.api.extensions.take([10, 20, 30], [0, 2])
# after
pd.api.extensions.take(np.array([10, 20, 30]), [0, 2])
Defensive patterns

Strategy: type-guard

Validate before calling

import numpy as np, pandas as pd

def safe_take(arr, indices, **kw):
    if not isinstance(arr, (np.ndarray, pd.Index, pd.Series, pd.api.extensions.ExtensionArray)):
        arr = np.asarray(arr)
    return pd.api.extensions.take(arr, indices, **kw)

Type guard

import numpy as np, pandas as pd

def is_takeable(arr) -> bool:
    return isinstance(arr, (np.ndarray, pd.Index, pd.Series, pd.api.extensions.ExtensionArray))

Prevention

When it happens

Trigger: pd.api.extensions.take([10, 20, 30], [0, 1]) with a Python list; passing a set or tuple; passing a scalar value where an array is required.

Common situations: Using pd.api.extensions.take as a generic indexing helper with native lists; refactors that drop the np.asarray conversion before calling take.

Related errors


AI-assisted analysis of pandas-dev/pandas@71959b8cb9 (2026-08-07). Data as JSON: /api/errors/ec18464f3e38a607. Report an issue: GitHub.