Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions pandas-stubs/core/frame.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -1317,18 +1317,18 @@ class DataFrame(NDFrame, OpsMixin, _GetItemHack):
) -> Self: ...
@overload
def stack(
self, level: Level | list[Level] = ..., dropna: _bool = ..., sort: _bool = ...
self, level: IndexLabel = ..., dropna: _bool = ..., sort: _bool = ...
) -> Self | Series: ...
@overload
def stack(
self, level: Level | list[Level] = ..., future_stack: _bool = ...
self, level: IndexLabel = ..., future_stack: _bool = ...
) -> Self | Series: ...
def explode(
self, column: Sequence[Hashable], ignore_index: _bool = ...
) -> Self: ...
def unstack(
self,
level: Level = ...,
level: IndexLabel = ...,
fill_value: Scalar | None = ...,
sort: _bool = ...,
) -> Self | Series: ...
Expand Down
2 changes: 1 addition & 1 deletion pandas-stubs/core/series.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -934,7 +934,7 @@ class Series(IndexOpsMixin[S1], NDFrame):
def explode(self) -> Series[S1]: ...
def unstack(
self,
level: Level = ...,
level: IndexLabel = ...,
fill_value: int | _str | dict | None = ...,
) -> DataFrame: ...
@overload
Expand Down
1 change: 1 addition & 0 deletions tests/test_frame.py
Original file line number Diff line number Diff line change
Expand Up @@ -4461,6 +4461,7 @@ def test_unstack() -> None:
).set_index([0, 1])

check(assert_type(df.unstack(0), pd.DataFrame | pd.Series), pd.DataFrame)
check(assert_type(df.unstack([0]), pd.DataFrame | pd.Series), pd.DataFrame)
check(
assert_type(
df.unstack(1, fill_value=pd.Timestamp(2023, 4, 5)), pd.DataFrame | pd.Series
Expand Down
13 changes: 12 additions & 1 deletion tests/test_series.py
Original file line number Diff line number Diff line change
Expand Up @@ -3902,11 +3902,22 @@ def test_series_items() -> None:


def test_cumsum_timedelta() -> None:

s = pd.Series(pd.to_timedelta([1, 2, 3], "h"))
check(assert_type(s.cumsum(), "TimedeltaSeries"), pd.Series, pd.Timedelta)
check(
assert_type(pd.Timestamp(0) + s.cumsum(), "TimestampSeries"),
pd.Series,
pd.Timestamp,
)


def test_series_unstack() -> None:
df = pd.DataFrame([[1, 3, 5], [2, 4, 6]])
s = df.transpose().stack([*range(df.index.nlevels)])
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you do check(assert_type(s, pd.Series), pd.Series, np.int64) here? (I think that's the right type)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That fails with:

tests/test_series.py:3917: error: Expression is of type "DataFrame | Series[Any]", not "Series[Any]"  [assert-type]
Found 1 error in 1 file (checked 224 source files)

What I can do instead is:

def test_series_unstack() -> None:
    df = pd.DataFrame([[1, 3, 5], [2, 4, 6]])
    s = cast(pd.Series, df.transpose().stack([*range(df.index.nlevels)]))
    check(assert_type(s, pd.Series), pd.Series, np.int64)
    check(
        assert_type(
            s.unstack([*range(s.index.nlevels // 2)]),
            pd.DataFrame,
        ),
        pd.DataFrame,
    )

where I explicitly cast the stacked object to a Series. Or would you rather have something else there?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Replace s = cast(pd.Series, df.transpose().stack([*range(df.index.nlevels)])) with

s = df.transpose().stack([*range(df.index.nlevels)]))
check(assert_type(s, Union[pd.Series, pd.DataFrame), pd.Series)

This then says from a typing perspective, you could get the Union, but at runtime, you will get a Series

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense -- updated the test.

check(
assert_type(
s.unstack([*range(s.index.nlevels // 2)]),
Union[pd.Series, pd.DataFrame],
),
pd.DataFrame,
)