From 0fbd5d9ab221b970d60df79ce69c49acecf7aa42 Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Thu, 25 Jul 2019 16:34:57 -0700 Subject: [PATCH 1/8] Cast complex data types to object type when hashing is needed. Coerce to complex type when sorting is required. --- pandas/core/algorithms.py | 9 +-- pandas/core/sorting.py | 5 ++ pandas/tests/test_complex.py | 111 +++++++++++++++++++++++++++++++++++ 3 files changed, 121 insertions(+), 4 deletions(-) create mode 100644 pandas/tests/test_complex.py diff --git a/pandas/core/algorithms.py b/pandas/core/algorithms.py index c7230dd7385c2..60b2cc3071794 100644 --- a/pandas/core/algorithms.py +++ b/pandas/core/algorithms.py @@ -103,10 +103,11 @@ def _ensure_data(values, dtype=None): # ignore the fact that we are casting to float # which discards complex parts - with catch_warnings(): - simplefilter("ignore", np.ComplexWarning) - values = ensure_float64(values) - return values, "float64", "float64" + # with catch_warnings(): + # simplefilter("ignore", np.ComplexWarning) + # values = ensure_float64(values) + # return values, "float64", "float64" + return ensure_object(np.asarray(values)), "object", "object" except (TypeError, ValueError, OverflowError): # if we are trying to coerce to a dtype diff --git a/pandas/core/sorting.py b/pandas/core/sorting.py index 5f3ed87424d0e..8434e8ef67614 100644 --- a/pandas/core/sorting.py +++ b/pandas/core/sorting.py @@ -445,6 +445,11 @@ def safe_sort(values, labels=None, na_sentinel=-1, assume_unique=False, verify=T dtype, _ = infer_dtype_from_array(values) values = np.asarray(values, dtype=dtype) + elif isinstance(values, np.ndarray) and values.dtype == object: + dtype = lib.infer_dtype(values) + if dtype == 'complex': + values = np.asarray(values, dtype=dtype) + def sort_mixed(values): # order ints before strings, safe in py3 str_pos = np.array([isinstance(x, str) for x in values], dtype=bool) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py new file mode 100644 index 0000000000000..90b544592e29b --- /dev/null +++ b/pandas/tests/test_complex.py @@ -0,0 +1,111 @@ +from datetime import datetime +from itertools import permutations +import struct + +import numpy as np +from numpy import nan +from numpy.random import RandomState +import pytest + +from pandas._libs import algos as libalgos, groupby as libgroupby, hashtable as ht +from pandas.compat.numpy import np_array_datetime64_compat +import pandas.util._test_decorators as td + +from pandas.core.dtypes.dtypes import CategoricalDtype as CDT + +import pandas as pd +from pandas import ( + Categorical, + CategoricalIndex, + DatetimeIndex, + Index, + IntervalIndex, + Series, + Timestamp, + DataFrame, + Index, + compat, +) +import pandas.core.algorithms as algos +from pandas.core.arrays import DatetimeArray +import pandas.core.common as com +from pandas.core.sorting import safe_sort +import pandas.util.testing as tm +from pandas.util.testing import assert_almost_equal + + +class TestComplexSupportBasic: + @pytest.mark.parametrize("array,expected", [ + ( + [1+1j, 0, 1, 1j, 1+2j], + Series([1, 1, 1, 1, 1], index=[1+2j, 1+1j, 1j, 1, 0]) + ), + ( + [1+2j, 0, 1j, 1, 1j, 1+1j], + # index is sorted by value counts in descending order by default + Series([2, 1, 1, 1, 1], index=[1j, 1+2j, 1+1j, 1, 0]) + ) + ]) + def test_value_counts(self, array, expected): + result = algos.value_counts(array) + tm.assert_series_equal(result, expected) + + + @pytest.mark.parametrize("array,expected", [ + ( + [1+1j, 0, 1, 1j, 1+2j, 1+2j], + np.array([(1+1j), 0j, (1+0j), 1j, (1+2j)], dtype=object) + ), + ]) + def test_unique(self, array, expected): + result = algos.unique(array) + assert np.array_equal(result, expected) + + @pytest.mark.parametrize("array,expected", [ + ( + [0, 1j, 1j, 1, 1+1j, 1+2j, 1+1j], + Series([False, False, True, False, False, False, True], dtype=bool) + ), + ]) + def test_duplicated(self, array, expected): + result = Series(array).duplicated() + tm.assert_series_equal(result, expected) + + @pytest.mark.parametrize("array,expected", [ + ( + [0, 1j, 1j, 1, 1+1j, 1+2j, 1+1j], + Series([False, True, True, False, True, True, True], dtype=bool) + ), + ]) + def test_isin(self, array, expected): + result = Series(array).isin([1j, 1+1j, 1+2j]) + tm.assert_series_equal(result, expected) + + @pytest.mark.parametrize("array,expected", [ + ( + [1, 2, 2 + 1j], + (np.array([0, 1, 2]), np.array([(1+0j), (2+0j), (2+1j)], dtype=object)) + ), + ]) + def test_factorize(self, array, expected): + result = pd.factorize(array) + assert len(result) == 2 + + for i, r in enumerate(result): + assert np.array_equal(r, expected[i]) + + @pytest.mark.parametrize("frame,expected", [ + ( + DataFrame([dict(a=1, b=1 + 1j), dict(a=1, b=1 + 2j)]), + DataFrame( + np.array([1, 1]), + index=Index([(1+1j), (1+2j)], dtype='object', name='b'), + columns=Index(['a'], dtype='object')) + ), + ]) + def test_groupby(self, frame, expected): + result = frame.groupby("b").count() + tm.assert_frame_equal(result, expected) + + + From 665e7a6c2aed062aaa11a383ee7510d8de6fa3ee Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Thu, 25 Jul 2019 16:41:23 -0700 Subject: [PATCH 2/8] This commit fixes #17927 --- pandas/tests/test_complex.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index 90b544592e29b..e63dac3e567c9 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -107,5 +107,3 @@ def test_groupby(self, frame, expected): result = frame.groupby("b").count() tm.assert_frame_equal(result, expected) - - From a1421feefdd7bff2e3ad214618f779542d93ac69 Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Thu, 25 Jul 2019 16:50:32 -0700 Subject: [PATCH 3/8] This commit fixes #17927 --- pandas/tests/test_complex.py | 62 +++++++++++------------------------- 1 file changed, 19 insertions(+), 43 deletions(-) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index e63dac3e567c9..5160476467334 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -1,93 +1,70 @@ -from datetime import datetime -from itertools import permutations -import struct - import numpy as np -from numpy import nan -from numpy.random import RandomState import pytest -from pandas._libs import algos as libalgos, groupby as libgroupby, hashtable as ht -from pandas.compat.numpy import np_array_datetime64_compat -import pandas.util._test_decorators as td - -from pandas.core.dtypes.dtypes import CategoricalDtype as CDT - import pandas as pd from pandas import ( - Categorical, - CategoricalIndex, - DatetimeIndex, Index, - IntervalIndex, Series, - Timestamp, DataFrame, - Index, - compat, ) import pandas.core.algorithms as algos -from pandas.core.arrays import DatetimeArray -import pandas.core.common as com -from pandas.core.sorting import safe_sort import pandas.util.testing as tm -from pandas.util.testing import assert_almost_equal class TestComplexSupportBasic: @pytest.mark.parametrize("array,expected", [ ( - [1+1j, 0, 1, 1j, 1+2j], - Series([1, 1, 1, 1, 1], index=[1+2j, 1+1j, 1j, 1, 0]) + [1 + 1j, 0, 1, 1j, 1 + 2j], + Series([1, 1, 1, 1, 1], index=[1 + 2j, 1 + 1j, 1j, 1, 0]) ), ( - [1+2j, 0, 1j, 1, 1j, 1+1j], + [1 + 2j, 0, 1j, 1, 1j, 1 + 1j], # index is sorted by value counts in descending order by default - Series([2, 1, 1, 1, 1], index=[1j, 1+2j, 1+1j, 1, 0]) + Series([2, 1, 1, 1, 1], index=[1j, 1 + 2j, 1 + 1j, 1, 0]) ) ]) - def test_value_counts(self, array, expected): + def test_value_counts(self, array, expected): result = algos.value_counts(array) tm.assert_series_equal(result, expected) - @pytest.mark.parametrize("array,expected", [ ( - [1+1j, 0, 1, 1j, 1+2j, 1+2j], - np.array([(1+1j), 0j, (1+0j), 1j, (1+2j)], dtype=object) + [1 + 1j, 0, 1, 1j, 1 + 2j, 1 + 2j], + np.array([(1 + 1j), 0j, (1 + 0j), 1j, (1 + 2j)], dtype=object) ), ]) - def test_unique(self, array, expected): + def test_unique(self, array, expected): result = algos.unique(array) assert np.array_equal(result, expected) @pytest.mark.parametrize("array,expected", [ ( - [0, 1j, 1j, 1, 1+1j, 1+2j, 1+1j], + [0, 1j, 1j, 1, 1 + 1j, 1 + 2j, 1 + 1j], Series([False, False, True, False, False, False, True], dtype=bool) ), ]) - def test_duplicated(self, array, expected): + def test_duplicated(self, array, expected): result = Series(array).duplicated() tm.assert_series_equal(result, expected) @pytest.mark.parametrize("array,expected", [ ( - [0, 1j, 1j, 1, 1+1j, 1+2j, 1+1j], + [0, 1j, 1j, 1, 1 + 1j, 1 + 2j, 1 + 1j], Series([False, True, True, False, True, True, True], dtype=bool) ), ]) - def test_isin(self, array, expected): - result = Series(array).isin([1j, 1+1j, 1+2j]) + def test_isin(self, array, expected): + result = Series(array).isin([1j, 1 + 1j, 1 + 2j]) tm.assert_series_equal(result, expected) @pytest.mark.parametrize("array,expected", [ ( [1, 2, 2 + 1j], - (np.array([0, 1, 2]), np.array([(1+0j), (2+0j), (2+1j)], dtype=object)) + (np.array([0, 1, 2]), np.array([(1 + 0j), (2 + 0j), (2 + 1j)], + dtype=object)) ), ]) - def test_factorize(self, array, expected): + def test_factorize(self, array, expected): result = pd.factorize(array) assert len(result) == 2 @@ -98,12 +75,11 @@ def test_factorize(self, array, expected): ( DataFrame([dict(a=1, b=1 + 1j), dict(a=1, b=1 + 2j)]), DataFrame( - np.array([1, 1]), - index=Index([(1+1j), (1+2j)], dtype='object', name='b'), + np.array([1, 1]), + index=Index([(1 + 1j), (1 + 2j)], dtype='object', name='b'), columns=Index(['a'], dtype='object')) ), ]) - def test_groupby(self, frame, expected): + def test_groupby(self, frame, expected): result = frame.groupby("b").count() tm.assert_frame_equal(result, expected) - From 7a168239a5d2ad8b644142e8f7266df1d17dfe5b Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Thu, 25 Jul 2019 19:01:38 -0700 Subject: [PATCH 4/8] Use pandas testing utilities for testing numpy array equality. Complex numbers should not be sortable according to test_complex_sorting. The user should specify sort=False when grouping a dataframe by a complex data type. --- pandas/core/algorithms.py | 9 +-------- pandas/core/sorting.py | 6 +----- pandas/tests/test_complex.py | 6 +++--- 3 files changed, 5 insertions(+), 16 deletions(-) diff --git a/pandas/core/algorithms.py b/pandas/core/algorithms.py index 24dd3a76a6846..0a726ba86f50a 100644 --- a/pandas/core/algorithms.py +++ b/pandas/core/algorithms.py @@ -101,14 +101,7 @@ def _ensure_data(values, dtype=None): elif is_object_dtype(values) and dtype is None: return ensure_object(np.asarray(values)), "object", "object" elif is_complex_dtype(values) or is_complex_dtype(dtype): - - # ignore the fact that we are casting to float - # which discards complex parts - # with catch_warnings(): - # simplefilter("ignore", np.ComplexWarning) - # values = ensure_float64(values) - # return values, "float64", "float64" - return ensure_object(np.asarray(values)), "object", "object" + raise TypeError("Complex data types not supported...Coercing to object") except (TypeError, ValueError, OverflowError): # if we are trying to coerce to a dtype diff --git a/pandas/core/sorting.py b/pandas/core/sorting.py index d9b77ea536009..7521e9f50fecf 100644 --- a/pandas/core/sorting.py +++ b/pandas/core/sorting.py @@ -11,6 +11,7 @@ is_categorical_dtype, is_extension_array_dtype, is_list_like, + is_object_dtype, ) from pandas.core.dtypes.missing import isna @@ -444,11 +445,6 @@ def safe_sort(values, labels=None, na_sentinel=-1, assume_unique=False, verify=T dtype, _ = infer_dtype_from_array(values) values = np.asarray(values, dtype=dtype) - elif isinstance(values, np.ndarray) and values.dtype == object: - dtype = lib.infer_dtype(values) - if dtype == 'complex': - values = np.asarray(values, dtype=dtype) - def sort_mixed(values): # order ints before strings, safe in py3 str_pos = np.array([isinstance(x, str) for x in values], dtype=bool) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index 5160476467334..26a3850b244d0 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -35,7 +35,7 @@ def test_value_counts(self, array, expected): ]) def test_unique(self, array, expected): result = algos.unique(array) - assert np.array_equal(result, expected) + tm.assert_numpy_array_equal(result, expected) @pytest.mark.parametrize("array,expected", [ ( @@ -69,7 +69,7 @@ def test_factorize(self, array, expected): assert len(result) == 2 for i, r in enumerate(result): - assert np.array_equal(r, expected[i]) + tm.assert_numpy_array_equal(r, expected[i]) @pytest.mark.parametrize("frame,expected", [ ( @@ -81,5 +81,5 @@ def test_factorize(self, array, expected): ), ]) def test_groupby(self, frame, expected): - result = frame.groupby("b").count() + result = frame.groupby("b", sort=False).count() tm.assert_frame_equal(result, expected) From 0bf66a9de971cd775bb835069d02d4d0dab2e83f Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Thu, 25 Jul 2019 19:34:42 -0700 Subject: [PATCH 5/8] specify 64 bit integer data type in the complex groupby test --- pandas/tests/test_complex.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index 26a3850b244d0..9d498aa29cf83 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -75,7 +75,7 @@ def test_factorize(self, array, expected): ( DataFrame([dict(a=1, b=1 + 1j), dict(a=1, b=1 + 2j)]), DataFrame( - np.array([1, 1]), + np.array([1, 1], dtype=np.int64), index=Index([(1 + 1j), (1 + 2j)], dtype='object', name='b'), columns=Index(['a'], dtype='object')) ), From 85edadbc53058923d70cc39424b111812a67fbfc Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Fri, 26 Jul 2019 07:17:27 -0700 Subject: [PATCH 6/8] Simple test cases for mode --- pandas/core/algorithms.py | 2 +- pandas/core/sorting.py | 1 - pandas/tests/test_complex.py | 41 ++++++++++++++++++++++++++++++++++-- 3 files changed, 40 insertions(+), 4 deletions(-) diff --git a/pandas/core/algorithms.py b/pandas/core/algorithms.py index 0a726ba86f50a..c795a1452ade2 100644 --- a/pandas/core/algorithms.py +++ b/pandas/core/algorithms.py @@ -4,7 +4,7 @@ """ from textwrap import dedent from typing import Dict -from warnings import catch_warnings, simplefilter, warn +from warnings import warn import numpy as np diff --git a/pandas/core/sorting.py b/pandas/core/sorting.py index 7521e9f50fecf..46e8e97c7de8a 100644 --- a/pandas/core/sorting.py +++ b/pandas/core/sorting.py @@ -11,7 +11,6 @@ is_categorical_dtype, is_extension_array_dtype, is_list_like, - is_object_dtype, ) from pandas.core.dtypes.missing import isna diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index 9d498aa29cf83..71091c0ad608a 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -60,8 +60,8 @@ def test_isin(self, array, expected): @pytest.mark.parametrize("array,expected", [ ( [1, 2, 2 + 1j], - (np.array([0, 1, 2]), np.array([(1 + 0j), (2 + 0j), (2 + 1j)], - dtype=object)) + (np.array([0, 1, 2], dtype=np.int64), + np.array([(1 + 0j), (2 + 0j), (2 + 1j)], dtype=object)) ), ]) def test_factorize(self, array, expected): @@ -83,3 +83,40 @@ def test_factorize(self, array, expected): def test_groupby(self, frame, expected): result = frame.groupby("b", sort=False).count() tm.assert_frame_equal(result, expected) + + # sorting of the index should fail since complex numbers are unordered + with pytest.raises(TypeError): + frame.groupby("b", sort=True).count() + + @pytest.mark.parametrize("array,expected", [ + ( + [0, 1j, 1, 1, 1 + 1j, 1 + 2j], + Series([1], dtype=np.complex128) + ), + ( + [1 + 1j, 2j, 1 + 1j], + Series([1 + 1j], dtype=np.complex128) + ), + ]) + def test_unimode(self, array, expected): + result = Series(array).mode() + tm.assert_series_equal(result, expected) + + @pytest.mark.parametrize("array,expected", [ + ( + # no modes + [0, 1j, 1, 1 + 1j, 1 + 2j], + Series([0, 1, 1j, 1 + 1j, 1 + 2j], dtype=np.complex128) + ), + ( + [1 + 1j, 2j, 1 + 1j, 2j, 3], + Series([1 + 1j, 2j], dtype=np.complex128) + ), + ]) + def test_multimode(self, array, expected): + # mode tries to sort multimodal series. + # A warning will be raise since complex numbers + # are not ordered. + with pytest.warns(UserWarning): + result = Series(array).mode() + tm.assert_series_equal(result, expected) From 0a1e59acf2abc87ce4eddd400bdf4f3b2396ea48 Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Tue, 30 Jul 2019 19:03:25 -0700 Subject: [PATCH 7/8] change bit specific integer types to platform dependent integers in test_factorize. --- pandas/tests/test_complex.py | 160 ++++++++++++++++++----------------- 1 file changed, 81 insertions(+), 79 deletions(-) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index 71091c0ad608a..a05df55bfe681 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -2,84 +2,90 @@ import pytest import pandas as pd -from pandas import ( - Index, - Series, - DataFrame, -) +from pandas import DataFrame, Index, Series import pandas.core.algorithms as algos import pandas.util.testing as tm class TestComplexSupportBasic: - @pytest.mark.parametrize("array,expected", [ - ( - [1 + 1j, 0, 1, 1j, 1 + 2j], - Series([1, 1, 1, 1, 1], index=[1 + 2j, 1 + 1j, 1j, 1, 0]) - ), - ( - [1 + 2j, 0, 1j, 1, 1j, 1 + 1j], - # index is sorted by value counts in descending order by default - Series([2, 1, 1, 1, 1], index=[1j, 1 + 2j, 1 + 1j, 1, 0]) - ) - ]) + @pytest.mark.parametrize( + "array,expected", + [ + ( + [1 + 1j, 0, 1, 1j, 1 + 2j], + Series([1, 1, 1, 1, 1], index=[1 + 2j, 1 + 1j, 1j, 1, 0]), + ), + ( + [1 + 2j, 0, 1j, 1, 1j, 1 + 1j], + # index is sorted by value counts in descending order by default + Series([2, 1, 1, 1, 1], index=[1j, 1 + 2j, 1 + 1j, 1, 0]), + ), + ], + ) def test_value_counts(self, array, expected): result = algos.value_counts(array) tm.assert_series_equal(result, expected) - @pytest.mark.parametrize("array,expected", [ - ( - [1 + 1j, 0, 1, 1j, 1 + 2j, 1 + 2j], - np.array([(1 + 1j), 0j, (1 + 0j), 1j, (1 + 2j)], dtype=object) - ), - ]) + @pytest.mark.parametrize( + "array,expected", + [ + ( + [1 + 1j, 0, 1, 1j, 1 + 2j, 1 + 2j], + np.array([(1 + 1j), 0j, (1 + 0j), 1j, (1 + 2j)], dtype=object), + ) + ], + ) def test_unique(self, array, expected): result = algos.unique(array) tm.assert_numpy_array_equal(result, expected) - @pytest.mark.parametrize("array,expected", [ - ( - [0, 1j, 1j, 1, 1 + 1j, 1 + 2j, 1 + 1j], - Series([False, False, True, False, False, False, True], dtype=bool) - ), - ]) + @pytest.mark.parametrize( + "array,expected", + [ + ( + [0, 1j, 1j, 1, 1 + 1j, 1 + 2j, 1 + 1j], + Series([False, False, True, False, False, False, True], dtype=bool), + ) + ], + ) def test_duplicated(self, array, expected): result = Series(array).duplicated() tm.assert_series_equal(result, expected) - @pytest.mark.parametrize("array,expected", [ - ( - [0, 1j, 1j, 1, 1 + 1j, 1 + 2j, 1 + 1j], - Series([False, True, True, False, True, True, True], dtype=bool) - ), - ]) + @pytest.mark.parametrize( + "array,expected", + [ + ( + [0, 1j, 1j, 1, 1 + 1j, 1 + 2j, 1 + 1j], + Series([False, True, True, False, True, True, True], dtype=bool), + ) + ], + ) def test_isin(self, array, expected): result = Series(array).isin([1j, 1 + 1j, 1 + 2j]) tm.assert_series_equal(result, expected) - @pytest.mark.parametrize("array,expected", [ - ( - [1, 2, 2 + 1j], - (np.array([0, 1, 2], dtype=np.int64), - np.array([(1 + 0j), (2 + 0j), (2 + 1j)], dtype=object)) - ), - ]) - def test_factorize(self, array, expected): - result = pd.factorize(array) - assert len(result) == 2 + def test_factorize(self): + array = [1, 2, 2 + 1j] + labels, uniques = pd.factorize(array) + expected = np.array([0, 1, 2], dtype=np.intp) + tm.assert_numpy_array_equal(labels, expected) + expected = np.array([(1 + 0j), (2 + 0j), (2 + 1j)], dtype=object) + tm.assert_numpy_array_equal(uniques, expected) - for i, r in enumerate(result): - tm.assert_numpy_array_equal(r, expected[i]) - - @pytest.mark.parametrize("frame,expected", [ - ( - DataFrame([dict(a=1, b=1 + 1j), dict(a=1, b=1 + 2j)]), - DataFrame( - np.array([1, 1], dtype=np.int64), - index=Index([(1 + 1j), (1 + 2j)], dtype='object', name='b'), - columns=Index(['a'], dtype='object')) - ), - ]) + @pytest.mark.parametrize( + "frame,expected", + [ + ( + DataFrame([dict(a=1, b=1 + 1j), dict(a=1, b=1 + 2j)]), + DataFrame( + np.array([1, 1], dtype=np.intp), + index=Index([(1 + 1j), (1 + 2j)], dtype="object", name="b"), + columns=Index(["a"], dtype="object"), + ), + ) + ], + ) def test_groupby(self, frame, expected): result = frame.groupby("b", sort=False).count() tm.assert_frame_equal(result, expected) @@ -88,35 +94,31 @@ def test_groupby(self, frame, expected): with pytest.raises(TypeError): frame.groupby("b", sort=True).count() - @pytest.mark.parametrize("array,expected", [ - ( - [0, 1j, 1, 1, 1 + 1j, 1 + 2j], - Series([1], dtype=np.complex128) - ), - ( - [1 + 1j, 2j, 1 + 1j], - Series([1 + 1j], dtype=np.complex128) - ), - ]) + @pytest.mark.parametrize( + "array,expected", + [ + ([0, 1j, 1, 1, 1 + 1j, 1 + 2j], Series([1], dtype=np.complex128)), + ([1 + 1j, 2j, 1 + 1j], Series([1 + 1j], dtype=np.complex128)), + ], + ) def test_unimode(self, array, expected): result = Series(array).mode() tm.assert_series_equal(result, expected) - @pytest.mark.parametrize("array,expected", [ - ( - # no modes - [0, 1j, 1, 1 + 1j, 1 + 2j], - Series([0, 1, 1j, 1 + 1j, 1 + 2j], dtype=np.complex128) - ), - ( - [1 + 1j, 2j, 1 + 1j, 2j, 3], - Series([1 + 1j, 2j], dtype=np.complex128) - ), - ]) + @pytest.mark.parametrize( + "array,expected", + [ + ( + # no modes + [0, 1j, 1, 1 + 1j, 1 + 2j], + Series([0, 1, 1j, 1 + 1j, 1 + 2j], dtype=np.complex128), + ), + ([1 + 1j, 2j, 1 + 1j, 2j, 3], Series([1 + 1j, 2j], dtype=np.complex128)), + ], + ) def test_multimode(self, array, expected): # mode tries to sort multimodal series. # A warning will be raise since complex numbers # are not ordered. - with pytest.warns(UserWarning): - result = Series(array).mode() + result = Series(array).mode() tm.assert_series_equal(result, expected) From a8fba282fffc92172ab3f9b1a29030ff4ba37c95 Mon Sep 17 00:00:00 2001 From: Sergey Kojoian Date: Mon, 7 Oct 2019 15:55:38 -0700 Subject: [PATCH 8/8] update tests for basic complex number support. Use assert_produces_warning instead of pytest.warns to capture warnings --- pandas/tests/test_complex.py | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/pandas/tests/test_complex.py b/pandas/tests/test_complex.py index a05df55bfe681..9afe8c476f5ca 100644 --- a/pandas/tests/test_complex.py +++ b/pandas/tests/test_complex.py @@ -7,7 +7,7 @@ import pandas.util.testing as tm -class TestComplexSupportBasic: +class TestBasicComplexSupport: @pytest.mark.parametrize( "array,expected", [ @@ -79,7 +79,7 @@ def test_factorize(self): ( DataFrame([dict(a=1, b=1 + 1j), dict(a=1, b=1 + 2j)]), DataFrame( - np.array([1, 1], dtype=np.intp), + np.array([1, 1], dtype=np.int64), index=Index([(1 + 1j), (1 + 2j)], dtype="object", name="b"), columns=Index(["a"], dtype="object"), ), @@ -105,6 +105,9 @@ def test_unimode(self, array, expected): result = Series(array).mode() tm.assert_series_equal(result, expected) + # mode tries to sort multimodal series. + # A warning will be raised since complex numbers + # are not ordered. @pytest.mark.parametrize( "array,expected", [ @@ -117,8 +120,6 @@ def test_unimode(self, array, expected): ], ) def test_multimode(self, array, expected): - # mode tries to sort multimodal series. - # A warning will be raise since complex numbers - # are not ordered. - result = Series(array).mode() + with tm.assert_produces_warning(UserWarning): + result = Series(array).mode() tm.assert_series_equal(result, expected)