use crate::core::ChebyScalar;
#[inline]
pub fn tail_norm<T: ChebyScalar>(coeffs: &[T], from: usize) -> f64 {
coeffs.iter().skip(from).map(|c| c.magnitude()).sum()
}
#[inline]
pub fn estimated_truncation_error<T: ChebyScalar>(coeffs: &[T]) -> f64 {
if coeffs.is_empty() {
0.0
} else {
tail_norm(coeffs, (3 * coeffs.len()) / 4)
}
}
#[inline]
pub fn is_converged<T: ChebyScalar>(coeffs: &[T], abs_tol: f64, rel_tol: f64) -> bool {
let scale = coeffs
.iter()
.map(|c| c.magnitude())
.fold(0.0_f64, f64::max)
.max(1.0);
let tail_err = estimated_truncation_error(coeffs);
let trailing = coeffs
.iter()
.rev()
.take(3)
.map(|c| c.magnitude())
.fold(0.0_f64, f64::max);
let err = tail_err.max(trailing);
err <= abs_tol || err <= rel_tol * scale
}