Skip to content

Commit 9ed521e

Browse files
authored
REF: Fix PeriodIndex._outer_indexer -> share remaining set methods (#39331)
1 parent fc08415 commit 9ed521e

File tree

5 files changed

+19
-46
lines changed

5 files changed

+19
-46
lines changed

pandas/core/indexes/base.py

+3-3
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,7 @@
115115

116116
if TYPE_CHECKING:
117117
from pandas import MultiIndex, RangeIndex, Series
118+
from pandas.core.indexes.datetimelike import DatetimeIndexOpsMixin
118119

119120

120121
__all__ = ["Index"]
@@ -2895,9 +2896,8 @@ def _union(self, other, sort):
28952896

28962897
@final
28972898
def _wrap_setop_result(self, other, result):
2898-
if isinstance(self, (ABCDatetimeIndex, ABCTimedeltaIndex)) and isinstance(
2899-
result, np.ndarray
2900-
):
2899+
if needs_i8_conversion(self.dtype) and isinstance(result, np.ndarray):
2900+
self = cast("DatetimeIndexOpsMixin", self)
29012901
result = type(self._data)._simple_new(result, dtype=self.dtype)
29022902
elif is_categorical_dtype(self.dtype) and isinstance(result, np.ndarray):
29032903
result = Categorical(result, dtype=self.dtype)

pandas/core/indexes/datetimelike.py

+7-7
Original file line numberDiff line numberDiff line change
@@ -612,6 +612,13 @@ def insert(self, loc: int, item):
612612
# --------------------------------------------------------------------
613613
# Join/Set Methods
614614

615+
_inner_indexer = _join_i8_wrapper(libjoin.inner_join_indexer)
616+
_outer_indexer = _join_i8_wrapper(libjoin.outer_join_indexer)
617+
_left_indexer = _join_i8_wrapper(libjoin.left_join_indexer)
618+
_left_indexer_unique = _join_i8_wrapper(
619+
libjoin.left_join_indexer_unique, with_indexers=False
620+
)
621+
615622
def _get_join_freq(self, other):
616623
"""
617624
Get the freq to attach to the result of a join operation.
@@ -832,13 +839,6 @@ def _union(self, other, sort):
832839
# Join Methods
833840
_join_precedence = 10
834841

835-
_inner_indexer = _join_i8_wrapper(libjoin.inner_join_indexer)
836-
_outer_indexer = _join_i8_wrapper(libjoin.outer_join_indexer)
837-
_left_indexer = _join_i8_wrapper(libjoin.left_join_indexer)
838-
_left_indexer_unique = _join_i8_wrapper(
839-
libjoin.left_join_indexer_unique, with_indexers=False
840-
)
841-
842842
def join(
843843
self, other, how: str = "left", level=None, return_indexers=False, sort=False
844844
):

pandas/core/indexes/period.py

+1-28
Original file line numberDiff line numberDiff line change
@@ -31,12 +31,11 @@
3131
)
3232
import pandas.core.common as com
3333
import pandas.core.indexes.base as ibase
34-
from pandas.core.indexes.base import ensure_index, maybe_extract_name
34+
from pandas.core.indexes.base import maybe_extract_name
3535
from pandas.core.indexes.datetimelike import DatetimeIndexOpsMixin
3636
from pandas.core.indexes.datetimes import DatetimeIndex, Index
3737
from pandas.core.indexes.extension import inherit_names
3838
from pandas.core.indexes.numeric import Int64Index
39-
from pandas.core.ops import get_op_result_name
4039

4140
_index_doc_kwargs = dict(ibase._index_doc_kwargs)
4241
_index_doc_kwargs.update({"target_klass": "PeriodIndex or list of Periods"})
@@ -580,32 +579,6 @@ def _get_string_slice(self, key: str):
580579
except KeyError as err:
581580
raise KeyError(key) from err
582581

583-
# ------------------------------------------------------------------------
584-
# Set Operation Methods
585-
586-
def _setop(self, other, sort, opname: str):
587-
"""
588-
Perform a set operation by dispatching to the Int64Index implementation.
589-
"""
590-
self._validate_sort_keyword(sort)
591-
self._assert_can_do_setop(other)
592-
res_name = get_op_result_name(self, other)
593-
other = ensure_index(other)
594-
595-
i8self = Int64Index._simple_new(self.asi8)
596-
i8other = Int64Index._simple_new(other.asi8)
597-
i8result = getattr(i8self, opname)(i8other, sort=sort)
598-
599-
parr = type(self._data)(np.asarray(i8result, dtype=np.int64), dtype=self.dtype)
600-
result = type(self)._simple_new(parr, name=res_name)
601-
return result
602-
603-
def _intersection(self, other, sort=False):
604-
return self._setop(other, sort, opname="intersection")
605-
606-
def _union(self, other, sort):
607-
return self._setop(other, sort, opname="_union")
608-
609582
# ------------------------------------------------------------------------
610583

611584
def memory_usage(self, deep: bool = False) -> int:

pandas/core/indexes/range.py

-8
Original file line numberDiff line numberDiff line change
@@ -685,14 +685,6 @@ def symmetric_difference(self, other, result_name=None, sort=None):
685685

686686
# --------------------------------------------------------------------
687687

688-
@doc(Int64Index.join)
689-
def join(self, other, how="left", level=None, return_indexers=False, sort=False):
690-
if how == "outer" and self is not other:
691-
# note: could return RangeIndex in more circumstances
692-
return self._int64index.join(other, how, level, return_indexers, sort)
693-
694-
return super().join(other, how, level, return_indexers, sort)
695-
696688
def _concat(self, indexes, name):
697689
"""
698690
Overriding parent method for the case of all RangeIndex instances.

pandas/tests/indexes/period/test_join.py

+8
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,14 @@
88

99

1010
class TestJoin:
11+
def test_join_outer_indexer(self):
12+
pi = period_range("1/1/2000", "1/20/2000", freq="D")
13+
14+
result = pi._outer_indexer(pi._values, pi._values)
15+
tm.assert_numpy_array_equal(result[0], pi.asi8)
16+
tm.assert_numpy_array_equal(result[1], np.arange(len(pi), dtype=np.int64))
17+
tm.assert_numpy_array_equal(result[2], np.arange(len(pi), dtype=np.int64))
18+
1119
def test_joins(self, join_type):
1220
index = period_range("1/1/2000", "1/20/2000", freq="D")
1321

0 commit comments

Comments
 (0)