Skip to content

Commit 4cc834f

Browse files
authored
BUG: IntervalIndex.get_indexer with non-unique side (#62825)
1 parent 9da8705 commit 4cc834f

File tree

3 files changed

+24
-1
lines changed

3 files changed

+24
-1
lines changed

doc/source/whatsnew/v3.0.0.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1043,6 +1043,7 @@ Interval
10431043
- :meth:`Index.is_monotonic_decreasing`, :meth:`Index.is_monotonic_increasing`, and :meth:`Index.is_unique` could incorrectly be ``False`` for an ``Index`` created from a slice of another ``Index``. (:issue:`57911`)
10441044
- Bug in :class:`Index`, :class:`Series`, :class:`DataFrame` constructors when given a sequence of :class:`Interval` subclass objects casting them to :class:`Interval` (:issue:`46945`)
10451045
- Bug in :func:`interval_range` where start and end numeric types were always cast to 64 bit (:issue:`57268`)
1046+
- Bug in :meth:`IntervalIndex.get_indexer` and :meth:`IntervalIndex.drop` when one of the sides of the index is non-unique (:issue:`52245`)
10461047

10471048
Indexing
10481049
^^^^^^^^

pandas/core/indexes/interval.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -712,7 +712,10 @@ def _get_indexer(
712712
# -> at most one match per interval in target
713713
# want exact matches -> need both left/right to match, so defer to
714714
# left/right get_indexer, compare elementwise, equality -> match
715-
indexer = self._get_indexer_unique_sides(target)
715+
if self.left.is_unique and self.right.is_unique:
716+
indexer = self._get_indexer_unique_sides(target)
717+
else:
718+
indexer = self._get_indexer_pointwise(target)[0]
716719

717720
elif not (is_object_dtype(target.dtype) or is_string_dtype(target.dtype)):
718721
# homogeneous scalar index: use IntervalTree

pandas/tests/indexes/interval/test_indexing.py

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -503,6 +503,25 @@ def test_get_indexer_read_only(self):
503503
result = idx.get_indexer_non_unique(arr)[0]
504504
tm.assert_numpy_array_equal(result, expected, check_dtype=False)
505505

506+
def test_get_indexer_non_unique_right(self):
507+
# GH#52245
508+
data = [
509+
Interval(Timestamp("2020-05-26"), Timestamp("2020-05-27")),
510+
Interval(Timestamp("2020-05-27"), Timestamp("2020-05-27")),
511+
]
512+
513+
index = IntervalIndex(data)
514+
515+
result = index.get_indexer([index[0]])
516+
expected = np.array([0], dtype=np.intp)
517+
tm.assert_numpy_array_equal(result, expected)
518+
519+
# GH#52245 OP is about drop so we test that here, but the underlying
520+
# problem is in get_indexer.
521+
result = index.drop(index[0])
522+
expected = index[1:]
523+
tm.assert_index_equal(result, expected)
524+
506525

507526
class TestSliceLocs:
508527
def test_slice_locs_with_interval(self):

0 commit comments

Comments
 (0)