module Data.MovingAverage.SingleExponential ( singleExponential ) where import Data.MovingAverage.Types (MovingAverageError(..), SmoothedResults, buildSingleExponentialMovingAverage) singleExponential :: (Ord a, Floating a) => a -> [a] -> Either MovingAverageError (SmoothedResults a) singleExponential _ [] = Left NoValuesProvided singleExponential alpha xs | inRange 0 1 alpha = Right $ buildSingleExponentialMovingAverage alpha $ scanl go initialState (tail xs) | otherwise = Left $ InvalidAlphaValue "Alpha must be 0 <= a <= 1" where initialState = (head xs, head xs) go (_, previous) current = (current, s_t current previous) s_t current previous = alpha * current + (1 - alpha) * previous inRange :: Ord a => a -> a -> a -> Bool inRange min' max' value = value >= min' && value <= max'