You want the Constant
applicative from Data.Functor.Constant
in the transformers
package, which you can find here.
This Applicative
has the following instance:
instance (Monoid a) => Applicative (Constant a) where
pure _ = Constant mempty
Constant x <*> Constant y = Constant (x `mappend` y)
You can then compose Constant
with any other applicative using Compose
from Data.Functor.Compose
(also in the transformers
package), which you can find here.
Compose
has this Applicative
instance:
instance (Applicative f, Applicative g) => Applicative (Compose f g) where
pure x = Compose (pure (pure x))
Compose f <*> Compose x = Compose ((<*>) <$> f <*> x)
You can then Compose
your Constant
applicative with any other Applicative
(like State
) to keep both some state and a running Monoid
tally.
More generally, you should read the paper The Essence of the Iterator Pattern, which discusses these patterns in more detail.