auto-0.4.3.1: Denotative, locally stateful programming DSL & platform

Control.Auto.Generate

Description

This module contains various Autos that act as "producing" streams; they all ignore their input streams and produce output streams through a pure or monadic process.

Synopsis

# From lists

Arguments

 :: Serialize b => [b] list to output element-by-element -> Interval m a b

An Interval that ignores the input stream and just outputs items from the given list. Is "on" as long as there are still items in the list left, and "off" after there is nothing left in the list to output.

Serializes itself by storing the entire rest of the list in binary, so if your list is long, it might take up a lot of space upon storage. If your list is infinite, it makes an infinite binary, so be careful!

fromLongList can be used for longer lists or infinite lists; or, if your list can be boild down to an unfoldr, you can use unfold.

• Storing: O(n) time and space on length of remaining list
• Loading: O(1) time in the number of times the Auto has been stepped + O(n) time in the length of the remaining list.

Arguments

 :: [b] list to output element-by-element -> Interval m a b

The non-resuming/non-serializing version of fromList.

Arguments

 :: [b] list to output element-by-element -> Interval m a b

A version of fromList that is safe for long or infinite lists, or lists with unserializable elements.

There is a small cost in the time of loading/resuming, which is O(n) on the number of times the Auto had been stepped at the time of saving. This is because it has to drop the n first elements in the list, to "resume" to the proper position.

• Storing: O(1) time and space on the length of the remaining list
• Loading: O(n) time on the number of times the Auto has been stepped, maxing out at O(n) on the length of the entire input list.

# Constant producers

Here we have the "constant producers": Autos whose output is always the same value, or the result of executing the same monadic action.

pure   :: Monad m => b   -> Auto m a b
effect :: Monad m => m b -> Auto m a b


pure always outputs the same value, ignoring its input, and effect always outputs the result of executing the same monadic action, ignoring its input.

pure :: Applicative f => forall a. a -> f a #

Lift a value.

Arguments

 :: m b monadic action to contually execute. -> Auto m a b

To get every output, executes the monadic action and returns the result as the output. Always ignores input.

This is basically like an "effectful" pure:

pure   :: b   -> Auto m a b
effect :: m b -> Auto m a b


The output of pure is always the same, and the output of effect is always the result of the same monadic action. Both ignore their inputs.

Fun times when the underling Monad is, for instance, Reader.

>>> let a = effect ask    :: Auto (Reader b) a b
>>> let r = evalAuto a () :: Reader b b
>>> runReader r "hello"
"hello"
>>> runReader r 100
100


If your underling monad has effects (IO, State, Maybe, Writer, etc.), then it might be fun to take advantage of *> from Control.Applicative to "tack on" an effect to a normal Auto:

>>> let a = effect (modify (+1)) *> sumFrom 0 :: Auto (State Int) Int Int
>>> let st = streamAuto a [1..10]
>>> let (ys, s') = runState st 0
>>> ys
[1,3,6,10,15,21,28,36,45,55]
>>> s'
10


Our Auto a behaves exactly like sumFrom 0, except at each step, it also increments the underlying/global state by one. It is sumFrom 0 with an "attached effect".

# From functions

## Iterating

Arguments

 :: Serialize b => (b -> b) iterating function -> b starting value and initial output -> Auto m a b

Analogous to iterate from Prelude. Keeps accumulator value and continually applies the function to the accumulator at every step, outputting the result.

The first result is the initial accumulator value.

>>> take 10 . streamAuto' (iterator (*2) 1) $repeat () [1, 2, 4, 8, 16, 32, 64, 128, 256, 512]  Arguments  :: (b -> b) iterating function -> b starting value and initial output -> Auto m a b The non-resuming/non-serializing version of iterator. Arguments  :: (Serialize b, Monad m) => (b -> m b) (monadic) iterating function -> b starting value and initial output -> Auto m a b Like iterator, but with a monadic function. Arguments  :: Monad m => (b -> m b) (monadic) iterating function -> b starting value and initial output -> Auto m a b The non-resuming/non-serializing version of iteratorM. ## Enumerating results of a function Arguments  :: (Enum c, Serialize c) => (c -> b) discrete function -> c initial input -> Auto m a b Given a function from discrete enumerable inputs, iterates through all of the results of that function. >>> take 10 . streamAuto' (discreteF (^2) 0)$ repeat ()
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]


Arguments

 :: Enum c => (c -> b) discrete function -> c initial input -> Auto m a b

The non-resuming/non-serializing version of discreteF.

## Unfolding

"Iterating with state".

Arguments

 :: Serialize c => (c -> Maybe (b, c)) unfolding function -> c initial accumulator -> Interval m a b

Analogous to unfoldr from Prelude. Creates an Interval (that ignores its input) by maintaining an internal accumulator of type c and, at every step, applying to the unfolding function to the accumulator. If the result is Nothing, then the Interval will turn "off" forever (output Nothing forever); if the result is Just (y, acc), then it will output y and store acc as the new accumulator.

Given an initial accumulator.

>>> let countFromTil n m = flip unfold n $\i -> if i <= m  then Just (i, i+1) else Nothing >>> take 8 . streamAuto' (countFromTil 5 10)$ repeat ()
[Just 5, Just 6, Just 7, Just 8, Just 9, Just 10, Nothing, Nothing]


unfold f c0 behaves like overList (unfoldr f c0).

Arguments

 :: (c -> Maybe (b, c)) unfolding function -> c initial accumulator -> Interval m a b

The non-resuming & non-serializing version of unfold.

Arguments

 :: (Serialize c, Monad m) => (c -> m (Maybe (b, c))) unfolding function -> c initial accumulator -> Interval m a b

Like unfold, but the unfolding function is monadic.

Arguments

 :: Monad m => (c -> m (Maybe (b, c))) unfolding function -> c initial accumulator -> Interval m a b

The non-resuming & non-serializing version of unfoldM.

# Enumerating

Arguments

 :: (Serialize b, Enum b) => b initial value -> Auto m a b

Continually enumerate from the starting value, using succ.

Arguments

 :: Enum b => b initial value -> Auto m a b

The non-serializing/non-resuming version of enumFromA.