Skip to content

Commit c99dfea

Browse files
jbrockmendeljreback
authored andcommitted
BUG: PeriodArray comparisons inconsistent with Period comparisons (#30722)
1 parent 036dc88 commit c99dfea

File tree

4 files changed

+31
-8
lines changed

4 files changed

+31
-8
lines changed

doc/source/whatsnew/v1.0.0.rst

+1
Original file line numberDiff line numberDiff line change
@@ -837,6 +837,7 @@ Datetimelike
837837
- Bug in :class:`DatetimeArray`, :class:`TimedeltaArray`, and :class:`PeriodArray` where inplace addition and subtraction did not actually operate inplace (:issue:`24115`)
838838
- Bug in :func:`pandas.to_datetime` when called with ``Series`` storing ``IntegerArray`` raising ``TypeError`` instead of returning ``Series`` (:issue:`30050`)
839839
- Bug in :func:`date_range` with custom business hours as ``freq`` and given number of ``periods`` (:issue:`30593`)
840+
- Bug in :class:`PeriodIndex` comparisons with incorrectly casting integers to :class:`Period` objects, inconsistent with the :class:`Period` comparison behavior (:issue:`30722`)
840841

841842
Timedelta
842843
^^^^^^^^^

pandas/core/arrays/period.py

-6
Original file line numberDiff line numberDiff line change
@@ -73,19 +73,13 @@ def _period_array_cmp(cls, op):
7373

7474
@unpack_zerodim_and_defer(opname)
7575
def wrapper(self, other):
76-
ordinal_op = getattr(self.asi8, opname)
7776

7877
if isinstance(other, str):
7978
try:
8079
other = self._scalar_from_string(other)
8180
except ValueError:
8281
# string that can't be parsed as Period
8382
return invalid_comparison(self, other, op)
84-
elif isinstance(other, int):
85-
# TODO: sure we want to allow this? we dont for DTA/TDA
86-
# 2 tests rely on this
87-
other = Period(other, freq=self.freq)
88-
result = ordinal_op(other.ordinal)
8983

9084
if isinstance(other, self._recognized_scalars) or other is NaT:
9185
other = self._scalar_type(other)

pandas/tests/arithmetic/test_period.py

+29-1
Original file line numberDiff line numberDiff line change
@@ -127,14 +127,42 @@ def test_compare_object_dtype(self, box_with_array, other_box):
127127
class TestPeriodIndexComparisons:
128128
# TODO: parameterize over boxes
129129

130-
@pytest.mark.parametrize("other", ["2017", 2017])
130+
@pytest.mark.parametrize("other", ["2017", pd.Period("2017", freq="D")])
131131
def test_eq(self, other):
132132
idx = PeriodIndex(["2017", "2017", "2018"], freq="D")
133133
expected = np.array([True, True, False])
134134
result = idx == other
135135

136136
tm.assert_numpy_array_equal(result, expected)
137137

138+
@pytest.mark.parametrize(
139+
"other",
140+
[
141+
2017,
142+
[2017, 2017, 2017],
143+
np.array([2017, 2017, 2017]),
144+
np.array([2017, 2017, 2017], dtype=object),
145+
pd.Index([2017, 2017, 2017]),
146+
],
147+
)
148+
def test_eq_integer_disallowed(self, other):
149+
# match Period semantics by not treating integers as Periods
150+
151+
idx = PeriodIndex(["2017", "2017", "2018"], freq="D")
152+
expected = np.array([False, False, False])
153+
result = idx == other
154+
155+
tm.assert_numpy_array_equal(result, expected)
156+
157+
with pytest.raises(TypeError):
158+
idx < other
159+
with pytest.raises(TypeError):
160+
idx > other
161+
with pytest.raises(TypeError):
162+
idx <= other
163+
with pytest.raises(TypeError):
164+
idx >= other
165+
138166
def test_pi_cmp_period(self):
139167
idx = period_range("2007-01", periods=20, freq="M")
140168

pandas/tests/indexes/period/test_period.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -462,7 +462,7 @@ def test_index_duplicate_periods(self):
462462
ts = Series(np.random.randn(len(idx)), index=idx)
463463

464464
result = ts[2007]
465-
expected = ts[idx == 2007]
465+
expected = ts[idx == "2007"]
466466
tm.assert_series_equal(result, expected)
467467

468468
def test_index_unique(self):

0 commit comments

Comments
 (0)