diff --git a/src/awkward/operations/ak_corr.py b/src/awkward/operations/ak_corr.py index e646a43b0f..648fff27af 100644 --- a/src/awkward/operations/ak_corr.py +++ b/src/awkward/operations/ak_corr.py @@ -107,8 +107,33 @@ def _impl(x, y, weight, axis, keepdims, mask_identity, highlevel, behavior, attr ) x = ctx.wrap(x_layout) + x = ak.operations.ak_values_astype._impl( + x, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) y = ctx.wrap(y_layout) + y = ak.operations.ak_values_astype._impl( + y, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) weight = ctx.wrap(weight_layout, allow_other=True) + if weight is not None: + weight = ak.operations.ak_values_astype._impl( + weight, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) with np.errstate(invalid="ignore", divide="ignore"): xmean = ak.operations.ak_mean._impl( diff --git a/src/awkward/operations/ak_covar.py b/src/awkward/operations/ak_covar.py index 7c8fe930fe..3bf2275667 100644 --- a/src/awkward/operations/ak_covar.py +++ b/src/awkward/operations/ak_covar.py @@ -103,8 +103,33 @@ def _impl(x, y, weight, axis, keepdims, mask_identity, highlevel, behavior, attr ) x = ctx.wrap(x_layout) + x = ak.operations.ak_values_astype._impl( + x, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) y = ctx.wrap(y_layout) + y = ak.operations.ak_values_astype._impl( + y, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) weight = ctx.wrap(weight_layout, allow_other=True) + if weight is not None: + weight = ak.operations.ak_values_astype._impl( + weight, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) with np.errstate(invalid="ignore", divide="ignore"): xmean = ak.operations.ak_mean._impl( diff --git a/src/awkward/operations/ak_linear_fit.py b/src/awkward/operations/ak_linear_fit.py index 01ac0f3297..f0fe7b39ee 100644 --- a/src/awkward/operations/ak_linear_fit.py +++ b/src/awkward/operations/ak_linear_fit.py @@ -108,8 +108,33 @@ def _impl(x, y, weight, axis, keepdims, mask_identity, highlevel, behavior, attr ) x = ctx.wrap(x_layout) + x = ak.operations.ak_values_astype._impl( + x, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) y = ctx.wrap(y_layout) + y = ak.operations.ak_values_astype._impl( + y, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) weight = ctx.wrap(weight_layout, allow_other=True) + if weight is not None: + weight = ak.operations.ak_values_astype._impl( + weight, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) with np.errstate(invalid="ignore", divide="ignore"): if weight is None: diff --git a/src/awkward/operations/ak_mean.py b/src/awkward/operations/ak_mean.py index 5e51249d5a..13c1430973 100644 --- a/src/awkward/operations/ak_mean.py +++ b/src/awkward/operations/ak_mean.py @@ -193,7 +193,24 @@ def _impl(x, weight, axis, keepdims, mask_identity, highlevel, behavior, attrs): ) x = ctx.wrap(x_layout) + x = ak.operations.ak_values_astype._impl( + x, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) weight = ctx.wrap(weight_layout, allow_other=True) + if weight is not None: + weight = ak.operations.ak_values_astype._impl( + weight, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) # Handle named axis named_axis = _get_named_axis(ctx) diff --git a/src/awkward/operations/ak_moment.py b/src/awkward/operations/ak_moment.py index 882da992e2..91f0449caf 100644 --- a/src/awkward/operations/ak_moment.py +++ b/src/awkward/operations/ak_moment.py @@ -115,7 +115,24 @@ def _impl( ) x = ctx.wrap(x_layout) + x = ak.operations.ak_values_astype._impl( + x, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) weight = ctx.wrap(weight_layout, allow_other=True) + if weight is not None: + weight = ak.operations.ak_values_astype._impl( + weight, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) with np.errstate(invalid="ignore", divide="ignore"): if weight is None: diff --git a/src/awkward/operations/ak_var.py b/src/awkward/operations/ak_var.py index c2ecdea3e8..815a91f065 100644 --- a/src/awkward/operations/ak_var.py +++ b/src/awkward/operations/ak_var.py @@ -189,7 +189,24 @@ def _impl(x, weight, ddof, axis, keepdims, mask_identity, highlevel, behavior, a ) x = ctx.wrap(x_layout) + x = ak.operations.ak_values_astype._impl( + x, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) weight = ctx.wrap(weight_layout, allow_other=True) + if weight is not None: + weight = ak.operations.ak_values_astype._impl( + weight, + np.float64, + including_unknown=False, + highlevel=True, + behavior=ctx.behavior, + attrs=ctx.attrs, + ) # Handle named axis named_axis = _get_named_axis(ctx) diff --git a/tests/test_3527_descriptive_statistics_float64_casting.py b/tests/test_3527_descriptive_statistics_float64_casting.py new file mode 100644 index 0000000000..9d418d2de3 --- /dev/null +++ b/tests/test_3527_descriptive_statistics_float64_casting.py @@ -0,0 +1,33 @@ +# BSD 3-Clause License; see https://github.com/scikit-hep/awkward/blob/main/LICENSE + +from __future__ import annotations + +import numpy as np + +import awkward as ak + + +def test_int32_overflow(): + np.random.seed(42) + x = np.random.randint(2**21, 2**22, size=1000, dtype=np.int32) + y = np.random.randint(2**21, 2**22, size=1000, dtype=np.int32) + + np.testing.assert_allclose(np.sum(x), ak.sum(x)) + np.testing.assert_allclose(np.mean(x), ak.mean(x)) + np.testing.assert_allclose(np.var(x), ak.var(x)) + np.testing.assert_allclose(np.std(x), ak.std(x)) + np.testing.assert_allclose(np.cov(x, y, ddof=0)[0][1], ak.covar(x, y)) + np.testing.assert_allclose(np.corrcoef(x, y)[0][1], ak.corr(x, y)) + + +def test_int64_overflow(): + np.random.seed(42) + x = np.random.randint(2**61, 2**62, size=1000, dtype=np.int64) + y = np.random.randint(2**61, 2**62, size=1000, dtype=np.int64) + + np.testing.assert_allclose(np.sum(x), ak.sum(x)) + np.testing.assert_allclose(np.mean(x), ak.mean(x)) + np.testing.assert_allclose(np.var(x), ak.var(x)) + np.testing.assert_allclose(np.std(x), ak.std(x)) + np.testing.assert_allclose(np.cov(x, y, ddof=0)[0][1], ak.covar(x, y)) + np.testing.assert_allclose(np.corrcoef(x, y)[0][1], ak.corr(x, y))