From 88030f58f7e3e180866c452bf02e1177f2c7035a Mon Sep 17 00:00:00 2001 From: Vahid Tavanashad Date: Wed, 31 Jul 2024 12:59:51 -0500 Subject: [PATCH 1/3] unmute tests --- tests/test_fft.py | 78 +++++++++++++++++++++++++++++----------- tests/test_sycl_queue.py | 2 +- tests/test_umath.py | 2 +- 3 files changed, 59 insertions(+), 23 deletions(-) diff --git a/tests/test_fft.py b/tests/test_fft.py index 5d142f7e31a8..e003c5016678 100644 --- a/tests/test_fft.py +++ b/tests/test_fft.py @@ -13,14 +13,8 @@ get_all_dtypes, get_complex_dtypes, get_float_dtypes, - is_cpu_device, ) -# aspects of default device: -_def_device = dpctl.SyclQueue().sycl_device -_def_dev_has_fp64 = _def_device.has_aspect_fp64 -is_gpu_with_fp64 = not is_cpu_device() and _def_dev_has_fp64 - # TODO: `assert_dtype_allclose` calls in this file have `check_only_type_kind=True` # since stock NumPy is currently used in public CI for code coverege which @@ -391,11 +385,17 @@ def test_hfft_1D(self, dtype, n, norm): assert_dtype_allclose(result, expected, check_only_type_kind=True) @pytest.mark.parametrize("dtype", get_complex_dtypes()) - @pytest.mark.parametrize("n", [None, 5, 20]) + @pytest.mark.parametrize("n", [None, 5, 18]) @pytest.mark.parametrize("norm", ["forward", "backward", "ortho"]) def test_hfft_1D_complex(self, dtype, n, norm): x = dpnp.linspace(-1, 1, 11) a = dpnp.sin(x) + 1j * dpnp.cos(x) + # input should be Hermitian + a[0].imag = 0 + if n in [None, 18]: + f_ny = -1 if n is None else n // 2 # Nyquist mode + a[f_ny].imag = 0 + a[f_ny:] = 0 # no data needed after Nyquist mode a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) @@ -446,13 +446,18 @@ def test_fft_1D(self, dtype, n, norm): # but dpnp return float32 if input is float32 assert_dtype_allclose(result, expected, check_only_type_kind=True) - @pytest.mark.skipif(is_gpu_with_fp64, reason="MKLD17702") @pytest.mark.parametrize("dtype", get_complex_dtypes()) - @pytest.mark.parametrize("n", [None, 5, 20]) + @pytest.mark.parametrize("n", [None, 5, 18]) @pytest.mark.parametrize("norm", ["forward", "backward", "ortho"]) def test_fft_1D_complex(self, dtype, n, norm): x = dpnp.linspace(-1, 1, 11) a = dpnp.sin(x) + 1j * dpnp.cos(x) + # input should be Hermitian + a[0].imag = 0 + if n in [None, 18]: + f_ny = -1 if n is None else n // 2 # Nyquist mode + a[f_ny].imag = 0 + a[f_ny:] = 0 # no data needed after Nyquist mode a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) @@ -473,29 +478,55 @@ def test_fft_1D_on_2D_array(self, dtype, n, axis, norm, order): expected = numpy.fft.irfft(a_np, n=n, axis=axis, norm=norm) assert_dtype_allclose(result, expected, check_only_type_kind=True) - @pytest.mark.skipif(is_gpu_with_fp64, reason="MKLD17702") @pytest.mark.parametrize("dtype", get_complex_dtypes()) @pytest.mark.parametrize("n", [None, 5, 8]) @pytest.mark.parametrize("axis", [0, 1, 2]) @pytest.mark.parametrize("norm", ["forward", "backward", "ortho"]) @pytest.mark.parametrize("order", ["C", "F"]) def test_fft_1D_on_3D_array(self, dtype, n, axis, norm, order): - x1 = numpy.random.uniform(-10, 10, 24) - x2 = numpy.random.uniform(-10, 10, 24) + x1 = numpy.random.uniform(-10, 10, 120) + x2 = numpy.random.uniform(-10, 10, 120) a_np = numpy.array(x1 + 1j * x2, dtype=dtype).reshape( - 2, 3, 4, order=order + 4, 5, 6, order=order ) + # each 1-D array of input should be Hermitian + if axis == 0: + a_np[0].imag = 0 + if n is None: + # for axis=0 and n=8, Nyquist mode is not present + f_ny = -1 # Nyquist mode + a_np[-1].imag = 0 + elif axis == 1: + a_np[:, 0, :].imag = 0 + if n in [None, 8]: + f_ny = -1 # Nyquist mode + a_np[:, f_ny, :].imag = 0 + a_np[:, f_ny:, :] = 0 # no data needed after Nyquist mode + elif axis == 2: + a_np[..., 0].imag = 0 + if n in [None, 8]: + f_ny = -1 if n is None else n // 2 # Nyquist mode + a_np[..., f_ny].imag = 0 + a_np[..., f_ny:] = 0 # no data needed after Nyquist mode + a = dpnp.asarray(a_np) result = dpnp.fft.irfft(a, n=n, axis=axis, norm=norm) expected = numpy.fft.irfft(a_np, n=n, axis=axis, norm=norm) - assert_dtype_allclose(result, expected, check_only_type_kind=True) + assert_dtype_allclose( + result, expected, check_only_type_kind=True, factor=16 + ) - @pytest.mark.skipif(is_gpu_with_fp64, reason="MKLD17702") - @pytest.mark.parametrize("n", [None, 5, 20]) + @pytest.mark.parametrize("n", [None, 5, 18]) def test_fft_usm_ndarray(self, n): x = dpt.linspace(-1, 1, 11) a = dpt.sin(x) + 1j * dpt.cos(x) + # input should be Hermitian + a[0] = dpt.sin(x[0]) + if n in [None, 18]: + f_ny = -1 if n is None else n // 2 # Nyquist mode + a[f_ny] = dpt.sin(x[f_ny]) + a[f_ny:] = 0 # no data needed after Nyquist mode a_usm = dpt.asarray(a, dtype=dpt.complex64) a_np = dpt.asnumpy(a_usm) out_shape = n if n is not None else 2 * (a_usm.shape[0] - 1) @@ -506,13 +537,18 @@ def test_fft_usm_ndarray(self, n): expected = numpy.fft.irfft(a_np, n=n) assert_dtype_allclose(result, expected, check_only_type_kind=True) - @pytest.mark.skipif(is_gpu_with_fp64, reason="MKLD17702") @pytest.mark.parametrize("dtype", get_complex_dtypes()) - @pytest.mark.parametrize("n", [None, 5, 20]) + @pytest.mark.parametrize("n", [None, 5, 18]) @pytest.mark.parametrize("norm", ["forward", "backward", "ortho"]) def test_fft_1D_out(self, dtype, n, norm): x = dpnp.linspace(-1, 1, 11) a = dpnp.sin(x) + 1j * dpnp.cos(x) + # input should be Hermitian + a[0].imag = 0 + if n in [None, 18]: + f_ny = -1 if n is None else n // 2 # Nyquist mode + a[f_ny].imag = 0 + a[f_ny:] = 0 # no data needed after Nyquist mode a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) @@ -624,7 +660,7 @@ def test_fft_usm_ndarray(self, n): x = dpt.linspace(-1, 1, 11) a_usm = dpt.asarray(dpt.sin(x)) a_np = dpt.asnumpy(a_usm) - out_shape = a_usm.shape[0] // 2 + 1 if n is None else n // 2 + 1 + out_shape = a_usm.shape[0] // 2 + 1 if n is None else n // 2 out_dtype = map_dtype_to_device(dpnp.complex128, a_usm.sycl_device) out = dpt.empty(out_shape, dtype=out_dtype) @@ -642,7 +678,7 @@ def test_fft_1D_out(self, dtype, n, norm): a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) - out_shape = a.shape[0] // 2 + 1 if n is None else n // 2 + 1 + out_shape = a.shape[0] // 2 + 1 if n is None else n // 2 out_dtype = dpnp.complex64 if dtype == dpnp.float32 else dpnp.complex128 out = dpnp.empty(out_shape, dtype=out_dtype) @@ -661,7 +697,7 @@ def test_fft_1D_on_2D_array_out(self, dtype, n, axis, norm, order): a = dpnp.asarray(a_np) out_shape = list(a.shape) - out_shape[axis] = a.shape[axis] // 2 + 1 if n is None else n // 2 + 1 + out_shape[axis] = a.shape[axis] // 2 + 1 if n is None else n // 2 out_shape = tuple(out_shape) out_dtype = dpnp.complex64 if dtype == dpnp.float32 else dpnp.complex128 out = dpnp.empty(out_shape, dtype=out_dtype) diff --git a/tests/test_sycl_queue.py b/tests/test_sycl_queue.py index b35c18d50d2c..7fa0615a4fcb 100644 --- a/tests/test_sycl_queue.py +++ b/tests/test_sycl_queue.py @@ -1239,7 +1239,7 @@ def test_fft(func, device): expected = getattr(numpy.fft, func)(data) result = getattr(dpnp.fft, func)(dpnp_data) - assert_dtype_allclose(result, expected) + assert_dtype_allclose(result, expected, factor=16) expected_queue = dpnp_data.get_array().sycl_queue result_queue = result.get_array().sycl_queue diff --git a/tests/test_umath.py b/tests/test_umath.py index d272727e4693..c257ae986b04 100644 --- a/tests/test_umath.py +++ b/tests/test_umath.py @@ -313,7 +313,7 @@ def test_large_values(self, dtype): assert_dtype_allclose(result, expected) -class TestLogaddexp: +class TestLogAddExp: @pytest.mark.parametrize("dtype", get_all_dtypes(no_complex=True)) def test_logaddexp(self, dtype): np_array1, np_array2, expected = _get_numpy_arrays_2in_1out( From 425529e8bf911c3a6193269e641a1f728d29f545 Mon Sep 17 00:00:00 2001 From: Vahid Tavanashad Date: Fri, 2 Aug 2024 18:40:40 -0500 Subject: [PATCH 2/3] reverse unintended changes --- tests/test_fft.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/test_fft.py b/tests/test_fft.py index e003c5016678..467a966bb6ad 100644 --- a/tests/test_fft.py +++ b/tests/test_fft.py @@ -660,7 +660,7 @@ def test_fft_usm_ndarray(self, n): x = dpt.linspace(-1, 1, 11) a_usm = dpt.asarray(dpt.sin(x)) a_np = dpt.asnumpy(a_usm) - out_shape = a_usm.shape[0] // 2 + 1 if n is None else n // 2 + out_shape = a_usm.shape[0] // 2 + 1 if n is None else n // 2 + 1 out_dtype = map_dtype_to_device(dpnp.complex128, a_usm.sycl_device) out = dpt.empty(out_shape, dtype=out_dtype) @@ -678,7 +678,7 @@ def test_fft_1D_out(self, dtype, n, norm): a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) - out_shape = a.shape[0] // 2 + 1 if n is None else n // 2 + out_shape = a.shape[0] // 2 + 1 if n is None else n // 2 + 1 out_dtype = dpnp.complex64 if dtype == dpnp.float32 else dpnp.complex128 out = dpnp.empty(out_shape, dtype=out_dtype) @@ -697,7 +697,7 @@ def test_fft_1D_on_2D_array_out(self, dtype, n, axis, norm, order): a = dpnp.asarray(a_np) out_shape = list(a.shape) - out_shape[axis] = a.shape[axis] // 2 + 1 if n is None else n // 2 + out_shape[axis] = a.shape[axis] // 2 + 1 if n is None else n // 2 + 1 out_shape = tuple(out_shape) out_dtype = dpnp.complex64 if dtype == dpnp.float32 else dpnp.complex128 out = dpnp.empty(out_shape, dtype=out_dtype) From ac4afd611339bae5b2e1bba5594973ab6656662a Mon Sep 17 00:00:00 2001 From: Vahid Tavanashad Date: Mon, 5 Aug 2024 16:18:46 -0500 Subject: [PATCH 3/3] address comment --- tests/test_fft.py | 50 +++++++++++++++++++++++------------------------ 1 file changed, 24 insertions(+), 26 deletions(-) diff --git a/tests/test_fft.py b/tests/test_fft.py index 467a966bb6ad..b952baaf3674 100644 --- a/tests/test_fft.py +++ b/tests/test_fft.py @@ -16,6 +16,24 @@ ) +def _make_array_Hermitian(a, n): + """ + This function makes necessary changes of the input array of + `dpnp.fft.irfft` and `dpnp.fft.hfft` functions to make sure the + given array is Hermitian. + + """ + + a[0].imag = 0 + if n in [None, 18]: + # f_ny is Nyquist mode (n//2+1 mode) which is n//2 element + f_ny = -1 if n is None else n // 2 + a[f_ny].imag = 0 + a[f_ny:] = 0 # no data needed after Nyquist mode + + return a + + # TODO: `assert_dtype_allclose` calls in this file have `check_only_type_kind=True` # since stock NumPy is currently used in public CI for code coverege which # always returns complex128/float64 for FFT functions, but IntelĀ® NumPy and @@ -390,12 +408,7 @@ def test_hfft_1D(self, dtype, n, norm): def test_hfft_1D_complex(self, dtype, n, norm): x = dpnp.linspace(-1, 1, 11) a = dpnp.sin(x) + 1j * dpnp.cos(x) - # input should be Hermitian - a[0].imag = 0 - if n in [None, 18]: - f_ny = -1 if n is None else n // 2 # Nyquist mode - a[f_ny].imag = 0 - a[f_ny:] = 0 # no data needed after Nyquist mode + a = _make_array_Hermitian(a, n) a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) @@ -452,12 +465,7 @@ def test_fft_1D(self, dtype, n, norm): def test_fft_1D_complex(self, dtype, n, norm): x = dpnp.linspace(-1, 1, 11) a = dpnp.sin(x) + 1j * dpnp.cos(x) - # input should be Hermitian - a[0].imag = 0 - if n in [None, 18]: - f_ny = -1 if n is None else n // 2 # Nyquist mode - a[f_ny].imag = 0 - a[f_ny:] = 0 # no data needed after Nyquist mode + a = _make_array_Hermitian(a, n) a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a) @@ -519,14 +527,9 @@ def test_fft_1D_on_3D_array(self, dtype, n, axis, norm, order): @pytest.mark.parametrize("n", [None, 5, 18]) def test_fft_usm_ndarray(self, n): - x = dpt.linspace(-1, 1, 11) - a = dpt.sin(x) + 1j * dpt.cos(x) - # input should be Hermitian - a[0] = dpt.sin(x[0]) - if n in [None, 18]: - f_ny = -1 if n is None else n // 2 # Nyquist mode - a[f_ny] = dpt.sin(x[f_ny]) - a[f_ny:] = 0 # no data needed after Nyquist mode + x = dpnp.linspace(-1, 1, 11) + a = dpnp.sin(x) + 1j * dpnp.cos(x) + a = _make_array_Hermitian(a, n) a_usm = dpt.asarray(a, dtype=dpt.complex64) a_np = dpt.asnumpy(a_usm) out_shape = n if n is not None else 2 * (a_usm.shape[0] - 1) @@ -543,12 +546,7 @@ def test_fft_usm_ndarray(self, n): def test_fft_1D_out(self, dtype, n, norm): x = dpnp.linspace(-1, 1, 11) a = dpnp.sin(x) + 1j * dpnp.cos(x) - # input should be Hermitian - a[0].imag = 0 - if n in [None, 18]: - f_ny = -1 if n is None else n // 2 # Nyquist mode - a[f_ny].imag = 0 - a[f_ny:] = 0 # no data needed after Nyquist mode + a = _make_array_Hermitian(a, n) a = dpnp.asarray(a, dtype=dtype) a_np = dpnp.asnumpy(a)