Skip to content

Commit

Permalink
Added Series.dt.is_quarter_start and Series.dt.is_quarter_end (#9046)
Browse files Browse the repository at this point in the history
closes: #8679

Added `Series.dt` functions and tests for `is_quarter_start` and `is_quarter_end`.

Authors:
  - https://github.com/TravisHester
  - GALI PREM SAGAR (https://github.com/galipremsagar)

Approvers:
  - GALI PREM SAGAR (https://github.com/galipremsagar)
  - Marlene  (https://github.com/marlenezw)

URL: #9046
  • Loading branch information
TravisHester authored Aug 17, 2021
1 parent 62c9312 commit 3402fec
Show file tree
Hide file tree
Showing 2 changed files with 161 additions and 1 deletion.
96 changes: 95 additions & 1 deletion python/cudf/cudf/core/series.py
Original file line number Diff line number Diff line change
Expand Up @@ -6050,7 +6050,7 @@ def is_month_end(self):
-------
>>> import pandas as pd, cudf
>>> s = cudf.Series(
... pd.date_range(start='2000-08-026', end='2000-09-03', freq='1D'))
... pd.date_range(start='2000-08-26', end='2000-09-03', freq='1D'))
>>> s
0 2000-08-26
1 2000-08-27
Expand Down Expand Up @@ -6082,6 +6082,100 @@ def is_month_end(self):
)
return (self.day == last_day.dt.day).fillna(False)

@property
def is_quarter_start(self):
"""
Boolean indicator if the date is the first day of a quarter.
Returns
-------
Series
Booleans indicating if dates are the begining of a quarter
Example
-------
>>> import pandas as pd, cudf
>>> s = cudf.Series(
... pd.date_range(start='2000-09-26', end='2000-10-03', freq='1D'))
>>> s
0 2000-09-26
1 2000-09-27
2 2000-09-28
3 2000-09-29
4 2000-09-30
5 2000-10-01
6 2000-10-02
7 2000-10-03
dtype: datetime64[ns]
>>> s.dt.is_quarter_start
0 False
1 False
2 False
3 False
4 False
5 True
6 False
7 False
dtype: bool
"""
day = self.series._column.get_dt_field("day")
first_month = self.series._column.get_dt_field("month").isin(
[1, 4, 7, 10]
)

result = ((day == cudf.Scalar(1)) & first_month).fillna(False)
return Series._from_data(
{None: result}, index=self.series._index, name=self.series.name,
)

@property
def is_quarter_end(self):
"""
Boolean indicator if the date is the last day of a quarter.
Returns
-------
Series
Booleans indicating if dates are the end of a quarter
Example
-------
>>> import pandas as pd, cudf
>>> s = cudf.Series(
... pd.date_range(start='2000-09-26', end='2000-10-03', freq='1D'))
>>> s
0 2000-09-26
1 2000-09-27
2 2000-09-28
3 2000-09-29
4 2000-09-30
5 2000-10-01
6 2000-10-02
7 2000-10-03
dtype: datetime64[ns]
>>> s.dt.is_quarter_end
0 False
1 False
2 False
3 False
4 True
5 False
6 False
7 False
dtype: bool
"""
day = self.series._column.get_dt_field("day")
last_day = libcudf.datetime.last_day_of_month(self.series._column)
last_day = last_day.get_dt_field("day")
last_month = self.series._column.get_dt_field("month").isin(
[3, 6, 9, 12]
)

result = ((day == last_day) & last_month).fillna(False)
return Series._from_data(
{None: result}, index=self.series._index, name=self.series.name,
)

@property
def is_year_start(self):
"""
Expand Down
66 changes: 66 additions & 0 deletions python/cudf/cudf/tests/test_datetime.py
Original file line number Diff line number Diff line change
Expand Up @@ -1475,3 +1475,69 @@ def test_is_year_end(data, dtype):
got = gs.dt.is_year_end

assert_eq(expect, got)


@pytest.mark.parametrize(
"data",
[
[
"2020-05-01",
"2020-05-31",
"2020-02-29",
None,
"1999-12-01",
"2000-12-21",
None,
"1900-02-28",
"1800-03-14",
"2100-03-10",
"1970-04-1",
"1970-01-01",
"1969-12-11",
"2020-12-31",
]
],
)
@pytest.mark.parametrize("dtype", ["datetime64[ns]"])
def test_is_quarter_start(data, dtype):
# Series
ps = pd.Series(data, dtype=dtype)
gs = cudf.from_pandas(ps)

expect = ps.dt.is_quarter_start
got = gs.dt.is_quarter_start

assert_eq(expect, got)


@pytest.mark.parametrize(
"data",
[
[
"2020-05-01",
"2020-05-31",
"2020-02-29",
None,
"1999-12-01",
"2000-12-21",
None,
"1900-02-28",
"1800-03-14",
"2100-03-10",
"1970-04-1",
"1970-01-01",
"1969-12-11",
"2020-12-31",
]
],
)
@pytest.mark.parametrize("dtype", ["datetime64[ns]"])
def test_is_quarter_end(data, dtype):
# Series
ps = pd.Series(data, dtype=dtype)
gs = cudf.from_pandas(ps)

expect = ps.dt.is_quarter_end
got = gs.dt.is_quarter_end

assert_eq(expect, got)

0 comments on commit 3402fec

Please sign in to comment.