test_check_indexer.py 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105
  1. import numpy as np
  2. import pytest
  3. import pandas as pd
  4. import pandas._testing as tm
  5. from pandas.api.indexers import check_array_indexer
  6. @pytest.mark.parametrize(
  7. "indexer, expected",
  8. [
  9. # integer
  10. ([1, 2], np.array([1, 2], dtype=np.intp)),
  11. (np.array([1, 2], dtype="int64"), np.array([1, 2], dtype=np.intp)),
  12. (pd.array([1, 2], dtype="Int32"), np.array([1, 2], dtype=np.intp)),
  13. (pd.Index([1, 2]), np.array([1, 2], dtype=np.intp)),
  14. # boolean
  15. ([True, False, True], np.array([True, False, True], dtype=np.bool_)),
  16. (np.array([True, False, True]), np.array([True, False, True], dtype=np.bool_)),
  17. (
  18. pd.array([True, False, True], dtype="boolean"),
  19. np.array([True, False, True], dtype=np.bool_),
  20. ),
  21. # other
  22. ([], np.array([], dtype=np.intp)),
  23. ],
  24. )
  25. def test_valid_input(indexer, expected):
  26. arr = np.array([1, 2, 3])
  27. result = check_array_indexer(arr, indexer)
  28. tm.assert_numpy_array_equal(result, expected)
  29. @pytest.mark.parametrize(
  30. "indexer", [[True, False, None], pd.array([True, False, None], dtype="boolean")]
  31. )
  32. def test_boolean_na_returns_indexer(indexer):
  33. # https://github.com/pandas-dev/pandas/issues/31503
  34. arr = np.array([1, 2, 3])
  35. result = check_array_indexer(arr, indexer)
  36. expected = np.array([True, False, False], dtype=bool)
  37. tm.assert_numpy_array_equal(result, expected)
  38. @pytest.mark.parametrize(
  39. "indexer",
  40. [
  41. [True, False],
  42. pd.array([True, False], dtype="boolean"),
  43. np.array([True, False], dtype=np.bool_),
  44. ],
  45. )
  46. def test_bool_raise_length(indexer):
  47. arr = np.array([1, 2, 3])
  48. msg = "Boolean index has wrong length"
  49. with pytest.raises(IndexError, match=msg):
  50. check_array_indexer(arr, indexer)
  51. @pytest.mark.parametrize(
  52. "indexer", [[0, 1, None], pd.array([0, 1, pd.NA], dtype="Int64")]
  53. )
  54. def test_int_raise_missing_values(indexer):
  55. arr = np.array([1, 2, 3])
  56. msg = "Cannot index with an integer indexer containing NA values"
  57. with pytest.raises(ValueError, match=msg):
  58. check_array_indexer(arr, indexer)
  59. @pytest.mark.parametrize(
  60. "indexer",
  61. [
  62. [0.0, 1.0],
  63. np.array([1.0, 2.0], dtype="float64"),
  64. np.array([True, False], dtype=object),
  65. pd.Index([True, False], dtype=object),
  66. ],
  67. )
  68. def test_raise_invalid_array_dtypes(indexer):
  69. arr = np.array([1, 2, 3])
  70. msg = "arrays used as indices must be of integer or boolean type"
  71. with pytest.raises(IndexError, match=msg):
  72. check_array_indexer(arr, indexer)
  73. def test_raise_nullable_string_dtype(nullable_string_dtype):
  74. indexer = pd.array(["a", "b"], dtype=nullable_string_dtype)
  75. arr = np.array([1, 2, 3])
  76. msg = "arrays used as indices must be of integer or boolean type"
  77. with pytest.raises(IndexError, match=msg):
  78. check_array_indexer(arr, indexer)
  79. @pytest.mark.parametrize("indexer", [None, Ellipsis, slice(0, 3), (None,)])
  80. def test_pass_through_non_array_likes(indexer):
  81. arr = np.array([1, 2, 3])
  82. result = check_array_indexer(arr, indexer)
  83. assert result == indexer