pandas-dev/pandas · error · ValueError
'indices' must be an array, not a scalar
Error message
'indices' must be an array, not a scalar '{indices}'. What it means
ValueError from SparseArray.take when the indices argument is a scalar rather than array-like. take requires an iterable of integer positions because it builds a new SparseArray; scalar lookup should use __getitem__.
Solutions
- Wrap scalar indices in a list: arr.take([3]).
- Use arr[3] directly for single-element access.
- Validate: indices = np.atleast_1d(indices) before calling take.
Example fix
// before arr.take(3) # raises // after arr.take([3])
Defensive patterns
Strategy: validation
Validate before calling
import numpy as np
def take_safe(arr, indices):
return arr.take(np.atleast_1d(indices)) Type guard
def is_scalar_index(indices) -> bool:
import numbers
return isinstance(indices, numbers.Integral) Try / catch
try:
arr.take(indices)
except ValueError as e:
if 'must be an array' in str(e):
out = arr.take([indices])
else:
raise Prevention
- Always pass a list/array of positions to take.
- Use __getitem__ for single-element access.
- Wrap with np.atleast_1d in generic helpers.
When it happens
Trigger: arr.take(3) (scalar) instead of arr.take([3]); passing a python int where an array/list is expected.
Common situations: Generic code calling take with whatever value a caller supplied without wrapping; refactoring from arr[i] to .take.
Related errors
- Invalid value in 'indices'. Must be between -1 and the…
- can only insert Interval objects and NA into an…
- Cannot construct from scalar data. Pass a sequence instead.
- cannot do a non-empty take from an empty axes.
- Cannot slice with
AI-assisted analysis of pandas-dev/pandas@3b7651241d (2026-08-11).
Data as JSON: /api/errors/b12498609cecc8da.
Report an issue: GitHub.
Appendix: source
Thrown at pandas/core/arrays/sparse/array.py:1154
if loc < 0:
loc += n
if loc >= n or loc < 0:
raise IndexError(
f"index is out of bounds: must be an integer between -{n} and {n - 1}"
)
sp_loc = self.sp_index.lookup(loc)
if sp_loc == -1:
return self.fill_value
else:
val = self.sp_values[sp_loc]
val = maybe_box_datetimelike(val, self.sp_values.dtype)
return val
def take(self, indices, *, allow_fill: bool = False, fill_value=None) -> Self:
if is_scalar(indices):
raise ValueError(f"'indices' must be an array, not a scalar '{indices}'.")
indices = np.asarray(indices, dtype=np.int32)
dtype = None
if indices.size == 0:
result = np.array([], dtype="object")
dtype = self.dtype
elif allow_fill:
result = self._take_with_fill(indices, fill_value=fill_value)
else:
return self._take_without_fill(indices)
return type(self)(
result, fill_value=self.fill_value, kind=self.kind, dtype=dtype
)
def _take_with_fill(self, indices, fill_value=None) -> np.ndarray:
if fill_value is None:
fill_value = self.dtype.na_valueView on GitHub (pinned to 3b7651241d)