"""Util functions to help filter out similar results.""" from __future__ import annotations from collections.abc import Callable from datetime import datetime, timedelta import functools from typing import Any, ParamSpec, TypeVar, overload _R = TypeVar("_R", int, float, datetime) _P = ParamSpec("_P") @overload def ignore_variance( func: Callable[_P, int], ignored_variance: int ) -> Callable[_P, int]: ... @overload def ignore_variance( func: Callable[_P, float], ignored_variance: float ) -> Callable[_P, float]: ... @overload def ignore_variance( func: Callable[_P, datetime], ignored_variance: timedelta ) -> Callable[_P, datetime]: ... def ignore_variance(func: Callable[_P, _R], ignored_variance: Any) -> Callable[_P, _R]: """Wrap a function that returns old result if new result does not vary enough.""" last_value: _R | None = None @functools.wraps(func) def wrapper(*args: _P.args, **kwargs: _P.kwargs) -> _R: nonlocal last_value value = func(*args, **kwargs) if last_value is not None and abs(value - last_value) < ignored_variance: return last_value last_value = value return value return wrapper