From 52b08cb25a6e21aea80f8d66cb214488d5e08483 Mon Sep 17 00:00:00 2001 From: Jaime Di Cristina <74217512+dicristina@users.noreply.github.com> Date: Sun, 25 Dec 2022 21:33:53 -0400 Subject: [PATCH 1/3] Issue where df.groupby.resample.size returns DF. --- doc/source/whatsnew/v1.5.3.rst | 1 + pandas/core/resample.py | 6 ++++++ pandas/tests/resample/test_resampler_grouper.py | 12 ++++++++++++ 3 files changed, 19 insertions(+) diff --git a/doc/source/whatsnew/v1.5.3.rst b/doc/source/whatsnew/v1.5.3.rst index 0cb8796e3fb5d..a5796ceaf5c09 100644 --- a/doc/source/whatsnew/v1.5.3.rst +++ b/doc/source/whatsnew/v1.5.3.rst @@ -30,6 +30,7 @@ Bug fixes - Bug in :meth:`.Styler.to_excel` leading to error when unrecognized ``border-style`` (e.g. ``"hair"``) provided to Excel writers (:issue:`48649`) - Bug when chaining several :meth:`.Styler.concat` calls, only the last styler was concatenated (:issue:`49207`) - Fixed bug when instantiating a :class:`DataFrame` subclass inheriting from ``typing.Generic`` that triggered a ``UserWarning`` on python 3.11 (:issue:`49649`) +- Fixed bug in :meth:`Resampler.size` which caused a wide :class:`DataFrame` to be returned instead of a :class:`Series` with :class:`MultiIndex` (:issue:`46826`) - .. --------------------------------------------------------------------------- diff --git a/pandas/core/resample.py b/pandas/core/resample.py index 555b47f5e2304..46106e95d2c72 100644 --- a/pandas/core/resample.py +++ b/pandas/core/resample.py @@ -989,6 +989,12 @@ def var( @doc(GroupBy.size) def size(self): result = self._downsample("size") + + # If the result is a non-empty DataFrame we stack to get a Series + # GH 46826 + if isinstance(result, ABCDataFrame) and not result.empty: + result = result.stack() + if not len(self.ax): from pandas import Series diff --git a/pandas/tests/resample/test_resampler_grouper.py b/pandas/tests/resample/test_resampler_grouper.py index 0432cf397067d..b7353dcabc3eb 100644 --- a/pandas/tests/resample/test_resampler_grouper.py +++ b/pandas/tests/resample/test_resampler_grouper.py @@ -515,3 +515,15 @@ def test_resample_empty_Dataframe(keys): expected.index.name = keys[0] tm.assert_frame_equal(result, expected) + + +@pytest.mark.parametrize("freq", ["D", "M", "Q", "A"]) +def test_groupby_resample_size_all_index_same(freq): + # GH 46826 + df = DataFrame( + {"A": [1] * 3 + [2] * 3 + [1] * 3 + [2] * 3, "B": np.arange(12)}, + index=date_range("31/12/2000 18:00", freq="H", periods=12), + ) + result = df.groupby("A").resample(freq).size() + expected = df.groupby(["A", pd.Grouper(freq=freq)]).size() + tm.assert_series_equal(result, expected) From 02a9ae7c82393c7580c116f54d486110e1e7a319 Mon Sep 17 00:00:00 2001 From: Jaime Di Cristina <74217512+dicristina@users.noreply.github.com> Date: Tue, 27 Dec 2022 15:39:55 -0400 Subject: [PATCH 2/3] Expected result is manually constructed. --- .../tests/resample/test_resampler_grouper.py | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/pandas/tests/resample/test_resampler_grouper.py b/pandas/tests/resample/test_resampler_grouper.py index b7353dcabc3eb..a521e24aa6022 100644 --- a/pandas/tests/resample/test_resampler_grouper.py +++ b/pandas/tests/resample/test_resampler_grouper.py @@ -517,13 +517,23 @@ def test_resample_empty_Dataframe(keys): tm.assert_frame_equal(result, expected) -@pytest.mark.parametrize("freq", ["D", "M", "Q", "A"]) -def test_groupby_resample_size_all_index_same(freq): +def test_groupby_resample_size_all_index_same(): # GH 46826 df = DataFrame( {"A": [1] * 3 + [2] * 3 + [1] * 3 + [2] * 3, "B": np.arange(12)}, index=date_range("31/12/2000 18:00", freq="H", periods=12), ) - result = df.groupby("A").resample(freq).size() - expected = df.groupby(["A", pd.Grouper(freq=freq)]).size() + result = df.groupby("A").resample("D").size() + expected = Series( + 3, + index=pd.MultiIndex.from_tuples( + [ + (1, Timestamp("2000-12-31")), + (1, Timestamp("2001-01-01")), + (2, Timestamp("2000-12-31")), + (2, Timestamp("2001-01-01")), + ], + names=["A", None], + ), + ) tm.assert_series_equal(result, expected) From 2524d646a1395f95220c31a051cd13563ba49451 Mon Sep 17 00:00:00 2001 From: Jaime Di Cristina <74217512+dicristina@users.noreply.github.com> Date: Wed, 28 Dec 2022 14:27:49 -0400 Subject: [PATCH 3/3] Moved whatsnew entry to v2.0.0.rst. --- doc/source/whatsnew/v1.5.3.rst | 1 - doc/source/whatsnew/v2.0.0.rst | 1 + 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/source/whatsnew/v1.5.3.rst b/doc/source/whatsnew/v1.5.3.rst index a5796ceaf5c09..0cb8796e3fb5d 100644 --- a/doc/source/whatsnew/v1.5.3.rst +++ b/doc/source/whatsnew/v1.5.3.rst @@ -30,7 +30,6 @@ Bug fixes - Bug in :meth:`.Styler.to_excel` leading to error when unrecognized ``border-style`` (e.g. ``"hair"``) provided to Excel writers (:issue:`48649`) - Bug when chaining several :meth:`.Styler.concat` calls, only the last styler was concatenated (:issue:`49207`) - Fixed bug when instantiating a :class:`DataFrame` subclass inheriting from ``typing.Generic`` that triggered a ``UserWarning`` on python 3.11 (:issue:`49649`) -- Fixed bug in :meth:`Resampler.size` which caused a wide :class:`DataFrame` to be returned instead of a :class:`Series` with :class:`MultiIndex` (:issue:`46826`) - .. --------------------------------------------------------------------------- diff --git a/doc/source/whatsnew/v2.0.0.rst b/doc/source/whatsnew/v2.0.0.rst index 12b0d90e68ab9..0c173d07678b0 100644 --- a/doc/source/whatsnew/v2.0.0.rst +++ b/doc/source/whatsnew/v2.0.0.rst @@ -924,6 +924,7 @@ Groupby/resample/rolling - Bug in :meth:`.SeriesGroupBy.describe` with ``as_index=False`` would have the incorrect shape (:issue:`49256`) - Bug in :class:`.DataFrameGroupBy` and :class:`.SeriesGroupBy` with ``dropna=False`` would drop NA values when the grouper was categorical (:issue:`36327`) - Bug in :meth:`.SeriesGroupBy.nunique` would incorrectly raise when the grouper was an empty categorical and ``observed=True`` (:issue:`21334`) +- Bug in :meth:`Resampler.size` caused a wide :class:`DataFrame` to be returned instead of a :class:`Series` with :class:`MultiIndex` (:issue:`46826`) Reshaping ^^^^^^^^^