Skip to content
Open
Show file tree
Hide file tree
Changes from all 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
2 changes: 1 addition & 1 deletion xarray/core/indexes.py
Original file line number Diff line number Diff line change
Expand Up @@ -610,7 +610,7 @@ def _asarray_tuplesafe(values):

def _is_nested_tuple(possible_tuple):
return isinstance(possible_tuple, tuple) and any(
isinstance(value, tuple | list | slice) for value in possible_tuple
isinstance(value, list | slice) for value in possible_tuple
)


Expand Down
22 changes: 22 additions & 0 deletions xarray/tests/test_indexes.py
Original file line number Diff line number Diff line change
Expand Up @@ -509,6 +509,28 @@ def test_sel(self) -> None:
with pytest.raises(IndexError):
index.sel({"x": (slice(None), 1, "no_level")})

def test_sel_nested_tuple_key(self) -> None:
"""Test that tuple-valued MultiIndex levels can be selected with a single key.

Regression test for GH#11341: when a MultiIndex level contains tuples,
selecting with a nested tuple key ((1, 1), 2) should collapse the dimension
just like selecting with a non-nested tuple key (1, 2).
"""
# Create a MultiIndex where the first level contains tuples
nested_level_0 = pd.Index(
[(1, 1), (1, 1), (2, 2), (3, 3)], name="a", tupleize_cols=False
)
nested_level_1 = pd.Index([1, 2, 10, 20], name="b")
nested_mi = pd.MultiIndex.from_arrays([nested_level_0, nested_level_1])

index = PandasMultiIndex(nested_mi, "index")

# Select with a nested tuple key - should return scalar indexer
actual = index.sel({"index": ((1, 1), 2)})
# pandas.get_loc returns an integer for exact match
expected_dim_indexers = {"index": 1}
assert actual.dim_indexers == expected_dim_indexers

def test_join(self):
midx = pd.MultiIndex.from_product([["a", "aa"], [1, 2]], names=("one", "two"))
level_coords_dtype = {"one": "=U2", "two": "i"}
Expand Down
Loading