Skip to content

Commit e2fb53a

Browse files
committed
DEPR: Groupby obj, ax, indexer
1 parent e96627f commit e2fb53a

File tree

4 files changed

+66
-19
lines changed

4 files changed

+66
-19
lines changed

doc/source/whatsnew/v2.0.0.rst

+3
Original file line numberDiff line numberDiff line change
@@ -783,6 +783,9 @@ Deprecations
783783
- Deprecated calling ``float`` or ``int`` on a single element :class:`Series` to return a ``float`` or ``int`` respectively. Extract the element before calling ``float`` or ``int`` instead (:issue:`51101`)
784784
- Deprecated :meth:`Grouper.groups`, use :meth:`Groupby.groups` instead (:issue:`51182`)
785785
- Deprecated :meth:`Grouper.grouper`, use :meth:`Groupby.grouper` instead (:issue:`51182`)
786+
- Deprecated :meth:`Grouper.obj`, use :meth:`Groupby.obj` instead (:issue:`??`)
787+
- Deprecated :meth:`Grouper.indexer`, use :meth:`Resampler.indexer` instead (:issue:`??`)
788+
- Deprecated :meth:`Grouper.ax`, use :meth:`Resampler.ax` instead (:issue:`??`)
786789
-
787790

788791
.. ---------------------------------------------------------------------------

pandas/core/groupby/grouper.py

+46-15
Original file line numberDiff line numberDiff line change
@@ -270,21 +270,13 @@ def __init__(
270270
self.dropna = dropna
271271

272272
self._grouper_deprecated = None
273+
self._indexer_deprecated = None
274+
self._obj_deprecated = None
273275
self._gpr_index = None
274-
self.obj = None
275-
self.indexer = None
276276
self.binner = None
277277
self._grouper = None
278278
self._indexer = None
279279

280-
@final
281-
@property
282-
def ax(self) -> Index:
283-
index = self._gpr_index
284-
if index is None:
285-
raise ValueError("_set_grouper must be called before ax is accessed")
286-
return index
287-
288280
def _get_grouper(
289281
self, obj: NDFrameT, validate: bool = True
290282
) -> tuple[ops.BaseGrouper, NDFrameT]:
@@ -299,7 +291,7 @@ def _get_grouper(
299291
-------
300292
a tuple of grouper, obj (possibly sorted)
301293
"""
302-
obj, _ = self._set_grouper(obj)
294+
obj, _, _ = self._set_grouper(obj)
303295
grouper, _, obj = get_grouper(
304296
obj,
305297
[self.key],
@@ -335,17 +327,20 @@ def _set_grouper(
335327
-------
336328
NDFrame
337329
Index
330+
np.ndarray[np.intp] | None
338331
"""
339332
assert obj is not None
340333

334+
indexer = None
335+
341336
if self.key is not None and self.level is not None:
342337
raise ValueError("The Grouper cannot specify both a key and a level!")
343338

344339
# Keep self._grouper value before overriding
345340
if self._grouper is None:
346341
# TODO: What are we assuming about subsequent calls?
347342
self._grouper = gpr_index
348-
self._indexer = self.indexer
343+
self._indexer = self._indexer_deprecated
349344

350345
# the key must be a valid info item
351346
if self.key is not None:
@@ -387,17 +382,53 @@ def _set_grouper(
387382
if (self.sort or sort) and not ax.is_monotonic_increasing:
388383
# use stable sort to support first, last, nth
389384
# TODO: why does putting na_position="first" fix datetimelike cases?
390-
indexer = self.indexer = ax.array.argsort(
385+
indexer = self._indexer_deprecated = ax.array.argsort(
391386
kind="mergesort", na_position="first"
392387
)
393388
ax = ax.take(indexer)
394389
obj = obj.take(indexer, axis=self.axis)
395390

396391
# error: Incompatible types in assignment (expression has type
397392
# "NDFrameT", variable has type "None")
398-
self.obj = obj # type: ignore[assignment]
393+
self._obj_deprecated = obj # type: ignore[assignment]
399394
self._gpr_index = ax
400-
return obj, ax
395+
return obj, ax, indexer
396+
397+
@final
398+
@property
399+
def ax(self) -> Index:
400+
warnings.warn(
401+
f"{type(self).__name__}.ax is deprecated and will be removed in a "
402+
"future version. Use Resampler.ax instead",
403+
FutureWarning,
404+
stacklevel=find_stack_level(),
405+
)
406+
index = self._gpr_index
407+
if index is None:
408+
raise ValueError("_set_grouper must be called before ax is accessed")
409+
return index
410+
411+
@final
412+
@property
413+
def indexer(self):
414+
warnings.warn(
415+
f"{type(self).__name__}.indexer is deprecated and will be removed "
416+
"in a future version. Use Resampler.indexer instead.",
417+
FutureWarning,
418+
stacklevel=find_stack_level(),
419+
)
420+
return self._indexer_deprecated
421+
422+
@final
423+
@property
424+
def obj(self):
425+
warnings.warn(
426+
f"{type(self).__name__}.obj is deprecated and will be removed "
427+
"in a future version. Use GroupBy.indexer instead.",
428+
FutureWarning,
429+
stacklevel=find_stack_level(),
430+
)
431+
return self._obj_deprecated
401432

402433
@final
403434
@property

pandas/core/resample.py

+4-4
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,7 @@ class Resampler(BaseGroupBy, PandasObject):
133133
_timegrouper: TimeGrouper
134134
binner: DatetimeIndex | TimedeltaIndex | PeriodIndex # depends on subclass
135135
exclusions: frozenset[Hashable] = frozenset() # for SelectionMixin compat
136-
_internal_names_set = set({"obj", "ax"})
136+
_internal_names_set = set({"obj", "ax", "_indexer"})
137137

138138
# to the groupby descriptor
139139
_attributes = [
@@ -168,7 +168,7 @@ def __init__(
168168
self.group_keys = group_keys
169169
self.as_index = True
170170

171-
self.obj, self.ax = self._timegrouper._set_grouper(
171+
self.obj, self.ax, self._indexer = self._timegrouper._set_grouper(
172172
self._convert_obj(obj), sort=True, gpr_index=gpr_index
173173
)
174174
self.binner, self.grouper = self._get_binner()
@@ -235,7 +235,7 @@ def _get_binner(self):
235235
"""
236236
binner, bins, binlabels = self._get_binner_for_time()
237237
assert len(bins) == len(binlabels)
238-
bin_grouper = BinGrouper(bins, binlabels, indexer=self._timegrouper.indexer)
238+
bin_grouper = BinGrouper(bins, binlabels, indexer=self._indexer)
239239
return binner, bin_grouper
240240

241241
@Substitution(
@@ -1681,7 +1681,7 @@ def _get_resampler(self, obj: NDFrame, kind=None) -> Resampler:
16811681
TypeError if incompatible axis
16821682
16831683
"""
1684-
_, ax = self._set_grouper(obj, gpr_index=None)
1684+
_, ax, indexer = self._set_grouper(obj, gpr_index=None)
16851685

16861686
if isinstance(ax, DatetimeIndex):
16871687
return DatetimeIndexResampler(

pandas/tests/groupby/test_grouping.py

+13
Original file line numberDiff line numberDiff line change
@@ -1066,3 +1066,16 @@ def test_grouper_groups():
10661066
with tm.assert_produces_warning(FutureWarning, match=msg):
10671067
res = grper.grouper
10681068
assert res is gb.grouper
1069+
1070+
msg = "Grouper.obj is deprecated and will be removed"
1071+
with tm.assert_produces_warning(FutureWarning, match=msg):
1072+
res = grper.obj
1073+
assert res is gb.obj
1074+
1075+
msg = "Use Resampler.ax instead"
1076+
with tm.assert_produces_warning(FutureWarning, match=msg):
1077+
grper.ax
1078+
1079+
msg = "Grouper.indexer is deprecated"
1080+
with tm.assert_produces_warning(FutureWarning, match=msg):
1081+
grper.indexer

0 commit comments

Comments
 (0)