diff --git a/pandas/core/ops/__init__.py b/pandas/core/ops/__init__.py index f1f4777cedbc5..0b85c94f4b90c 100644 --- a/pandas/core/ops/__init__.py +++ b/pandas/core/ops/__init__.py @@ -829,15 +829,19 @@ def wrapper(self, other): is_other_int_dtype = is_integer_dtype(other.dtype) other = other if is_other_int_dtype else fill_bool(other, self) - else: - # scalars, list, tuple, np.array - is_other_int_dtype = is_integer_dtype(np.asarray(other).dtype) - if is_list_like(other) and not isinstance(other, np.ndarray): - # TODO: Can we do this before the is_integer_dtype check? - # could the is_integer_dtype check be checking the wrong - # thing? e.g. other = [[0, 1], [2, 3], [4, 5]]? + elif is_list_like(other): + # list, tuple, np.ndarray + if not isinstance(other, np.ndarray): other = construct_1d_object_array_from_listlike(other) + is_other_int_dtype = is_integer_dtype(other.dtype) + other = type(self)(other) + other = other if is_other_int_dtype else fill_bool(other, self) + + else: + # i.e. scalar + is_other_int_dtype = lib.is_integer(other) + # TODO: use extract_array once we handle EA correctly, see GH#27959 ovalues = lib.values_from_object(other) diff --git a/pandas/tests/series/test_operators.py b/pandas/tests/series/test_operators.py index bf725a04de058..c2cf91e582c47 100644 --- a/pandas/tests/series/test_operators.py +++ b/pandas/tests/series/test_operators.py @@ -159,6 +159,41 @@ def test_logical_operators_bool_dtype_with_int(self): expected = s_tft assert_series_equal(res, expected) + def test_logical_ops_bool_dtype_with_ndarray(self): + # make sure we operate on ndarray the same as Series + left = pd.Series([True, True, True, False, True]) + right = [True, False, None, True, np.nan] + + expected = pd.Series([True, False, False, False, False]) + result = left & right + tm.assert_series_equal(result, expected) + result = left & np.array(right) + tm.assert_series_equal(result, expected) + result = left & pd.Index(right) + tm.assert_series_equal(result, expected) + result = left & pd.Series(right) + tm.assert_series_equal(result, expected) + + expected = pd.Series([True, True, True, True, True]) + result = left | right + tm.assert_series_equal(result, expected) + result = left | np.array(right) + tm.assert_series_equal(result, expected) + result = left | pd.Index(right) + tm.assert_series_equal(result, expected) + result = left | pd.Series(right) + tm.assert_series_equal(result, expected) + + expected = pd.Series([False, True, True, True, True]) + result = left ^ right + tm.assert_series_equal(result, expected) + result = left ^ np.array(right) + tm.assert_series_equal(result, expected) + result = left ^ pd.Index(right) + tm.assert_series_equal(result, expected) + result = left ^ pd.Series(right) + tm.assert_series_equal(result, expected) + def test_logical_operators_int_dtype_with_bool_dtype_and_reindex(self): # GH#9016: support bitwise op for integer types