35 auto [sx, sy, sw, sxx, syy, sxy] = state;
36 return load_state(sx, sy, sw, sxx, syy, sxy);
39 void operator()(T x, T y)
noexcept
55 void operator()(T x, T y, T w)
noexcept
57 T dx = (x * sum_w) - sum_x;
58 T dy = (y * sum_w) - sum_y;
64 T denom = sum_w * sum_w_old;
65 T f = eve::if_else(denom != T{0}, w / denom, T{0});
66 sum_xx += f * dx * dx;
67 sum_yy += f * dy * dy;
68 sum_xy += f * dx * dy;
74 requires eve::simd_value<T> && eve::simd_compatible_ptr<U, T>
75 inline void operator()(U
const* x, U
const* y)
noexcept
77 (*this)(T {x}, T {y});
81 requires eve::simd_value<T> && eve::simd_compatible_ptr<U, T>
82 inline void operator()(U
const* x, U
const* y, U
const* w)
noexcept
84 (*this)(T {x}, T {y}, T {w});
88 [[nodiscard]]
auto stats()
const noexcept -> std::tuple<double, double, double, double, double, double>
90 if constexpr (std::is_floating_point_v<T>) {
91 return {sum_w, sum_x, sum_y, sum_xx, sum_yy, sum_xy};
93 auto [sxx, syy, sxy] = combine(sum_w, sum_x, sum_y, sum_xx, sum_yy, sum_xy);
94 return {eve::reduce(sum_w), eve::reduce(sum_x), eve::reduce(sum_y), sxx, syy, sxy};
123 double sample_variance_x;
124 double sample_variance_y;
127 double sample_covariance;
132 auto [sw, sx, sy, sxx, syy, sxy] = accumulator.stats();
141 variance_x = sxx / sw;
142 variance_y = syy / sw;
143 sample_variance_x = sxx / (sw - 1);
144 sample_variance_y = syy / (sw - 1);
146 if (!(sxx > 0 && syy > 0)) {
147 correlation =
static_cast<double>(sxx == syy);
149 correlation = sxy / std::sqrt(sxx * syy);
152 covariance = sxy / sw;
153 sample_covariance = sxy / (sw - 1);