pandas-dev/pandas · error · IndexError
Column(s) already selected
Error message
Column(s) {self._selection} already selected What it means
Raised by SelectionMixin.__getitem__ when a selection has already been made on the group-like object (its `_selection` is not None) and the caller tries to index into it again. Because the object already represents a fixed column subset, further column selection is ambiguous and is rejected as IndexError, directing the user to restructure the selection.
Solutions
- Make the column selection once, at the groupby/rolling construction site, instead of chaining.
- Recreate the groupby/rolling object from the original DataFrame if a different column subset is needed.
- Access the underlying object via `.obj` and re-select from there.
Example fix
# before
g = df.groupby('a')['b']
g['c'] # IndexError: Column(s) b already selected
# after
g = df.groupby('a')[['b', 'c']] Defensive patterns
Strategy: validation
Validate before calling
def can_select_again(selection_obj) -> bool:
# SelectionMixin objects whose _selection is set will reject further indexing
return getattr(selection_obj, '_selection', None) is None Type guard
def selection_already_made(selection_obj) -> bool:
return getattr(selection_obj, '_selection', None) is not None Try / catch
try:
sub = group_selection[key]
except IndexError as e:
if 'already selected' in str(e):
sub = group_selection.obj[key] # re-select from the underlying object
else:
raise Prevention
- Make column selections once, at groupby/rolling construction, rather than chaining.
- If you need a different subset, recreate the groupby/rolling from the original DataFrame.
- Access the underlying object via .obj to re-select when needed.
When it happens
Trigger: Calling `g['col']` (or a list/tuple/Series/Index/array key) on a groupby/rolling/resampler selection object that was already created with a column selection, e.g. `df.groupby('a')['b']['c']`.
Common situations: Chaining selection operations on groupby/rolling objects; code refactors that combine a column selection with a later `.getitem` call.
Related errors
- can only convert an array of size 1 to a Python scalar
- cannot do a non-empty take
- Cannot perform with non-ordered Categorical
- Cannot use quantile with bool dtype
- Column not found
AI-assisted analysis of pandas-dev/pandas@3b7651241d (2026-08-11).
Data as JSON: /api/errors/93cfa4d6d21fd84f.
Report an issue: GitHub.
Appendix: source
Thrown at pandas/core/base.py:214
return self._selected_obj.ndim
@final
@cache_readonly
def _obj_with_exclusions(self):
if isinstance(self.obj, ABCSeries):
return self.obj
if self._selection is not None:
return self.obj[self._selection_list]
if len(self.exclusions) > 0:
return self.obj._drop_axis(self.exclusions, axis=1)
else:
return self.obj
def __getitem__(self, key):
if self._selection is not None:
raise IndexError(f"Column(s) {self._selection} already selected")
if isinstance(key, (list, tuple, ABCSeries, ABCIndex, np.ndarray)):
if len(self.obj.columns.intersection(key)) != len(set(key)):
bad_keys = list(set(key).difference(self.obj.columns))
raise KeyError(f"Columns not found: {str(bad_keys)[1:-1]}")
return self._gotitem(list(key), ndim=2)
else:
if key not in self.obj:
raise KeyError(f"Column not found: {key}")
ndim = self.obj[key].ndim
return self._gotitem(key, ndim=ndim)
def _gotitem(self, key, ndim: int, subset=None):
"""
sub-classes to define
return a sliced object
View on GitHub (pinned to 3b7651241d)