MayaFlux 0.5.0
Digital-First Multimedia Processing Framework
Loading...
Searching...
No Matches

◆ normalize_inplace()

MAYAFLUX_API void MayaFlux::Kinesis::Vision::normalize_inplace ( std::span< float >  data)

Stretch values to fill [0, 1] using the span's observed min and max.

No-op if min == max. Operates in-place.

Parameters
dataFloat span to normalise in-place.

Definition at line 353 of file PixelOps.cpp.

354{
355 if (data.empty())
356 return;
357
358 const Eigen::Index en = static_cast<Eigen::Index>(data.size());
359 auto m = Eigen::Map<Eigen::ArrayXf>(data.data(), en);
360 const float mn = m.minCoeff();
361 const float mx = m.maxCoeff();
362 const float range = mx - mn;
363 if (range == 0.0F)
364 return;
365
366 const float inv = 1.0F / range;
367 float* out = data.data();
368 const size_t n = data.size();
369
370#ifdef MAYAFLUX_ARCH_X64
371 const __m256 v_mn = _mm256_set1_ps(mn);
372 const __m256 v_inv = _mm256_set1_ps(inv);
373 size_t i = 0;
374 for (; i + 8 <= n; i += 8) {
375 __m256 v = _mm256_loadu_ps(out + i);
376 _mm256_storeu_ps(out + i, _mm256_mul_ps(_mm256_sub_ps(v, v_mn), v_inv));
377 }
378 for (; i < n; ++i)
379 out[i] = (out[i] - mn) * inv;
380
381#elif defined(MAYAFLUX_ARCH_ARM64)
382 const float32x4_t v_mn = vdupq_n_f32(mn);
383 const float32x4_t v_inv = vdupq_n_f32(inv);
384 size_t i = 0;
385 for (; i + 4 <= n; i += 4) {
386 float32x4_t v = vld1q_f32(out + i);
387 vst1q_f32(out + i, vmulq_f32(vsubq_f32(v, v_mn), v_inv));
388 }
389 for (; i < n; ++i)
390 out[i] = (out[i] - mn) * inv;
391
392#else
393 P::transform(P::par_unseq, data.begin(), data.end(), data.begin(),
394 [mn, inv](float v) { return (v - mn) * inv; });
395#endif
396}