| Safe Haskell | Trustworthy |
|---|---|
| Language | Haskell98 |
Control.LVish.DeepFrz
Description
The DeepFrz module provides a way to return arbitrarily complex data
structures containing LVars from Par computations.
The important thing to know is that to use runParThenFreeze to run a
Par computation, you must make sure that all types you return from
the Par computation have DeepFrz instances. This means that, if
you wish to return a user-defined type, you will need to include a bit
of boilerplate to give it a DeepFrz instance. Here is a complete
example:
import Control.LVish.DeepFrz data MyData = MyData Int deriving Show instance DeepFrz MyData where type FrzType MyData = MyData main = print (runParThenFreeze (return (MyData 3)))
The functions you'll want to use
runParThenFreeze :: DeepFrz a => Par Det NonFrzn a -> FrzType a Source
Under normal conditions, calling a freeze operation inside a
Par computation makes the Par computation quasi-deterministic.
However, if we freeze only after all LVar operations are completed
(after the implicit global barrier of runPar), then we've avoided
all data races, and freezing is therefore safe. Running a Par
computation with runParThenFreeze accomplishes this, without our
having to call freeze explicitly.
In order to use runParThenFreeze, the type returned from the
Par computation must be a member of the DeepFrz class. All the
Data.LVar.* libraries should provide instances of DeepFrz
already. Further, you can create additional instances for custom,
pure datatypes. The result of a runParThenFreeze depends on the
type-level function FrzType, whose only purpose is to toggle the
s parameters of all IVars to the Frzn state.
Significantly, the freeze at the end of runParThenFreeze has no runtime cost, in
spite of the fact that it enables a deep (recursive) freeze of the value returned
by the Par computation.
runParThenFreezeIO :: DeepFrz a => Par d NonFrzn a -> IO (FrzType a) Source
This version works for nondeterministic computations as well.
Of course, nondeterministic computations may also call freeze
internally, but this function has an advantage to doing your own
freeze at the end of a runParIO: there is an implicit barrier
before the final freeze. Further, DeepFrz has no runtime
overhead, whereas regular freezing has a cost.
Some supporting types
DeepFreezing is a type-level (guaranteed O(1) time complexity)
operation. It marks an LVar and its contents (recursively) as
frozen. DeepFreezing is not an action that can be taken directly
by the user, however. Rather, it is the final step in a
runParThenFreeze invocation.
Associated Types
This type function is public. It maps pre-frozen types to frozen ones. It should be idempotent.
Instances
This exists only for the purpose of being a type which is not equal to Frzn.
One could just as well have used (), but this is more descriptive.
An uninhabited type that signals that an LVar has been frozen.
LVars should use this in place of their s parameter.
Instances
| Foldable (IStructure Frzn) | |
| Foldable (ISet Frzn) | |
| Foldable (ISet Frzn) | |
| Show a => Show (IVar Frzn a) | |
| Show a => Show (IStructure Frzn a) | |
| Show a => Show (ISet Frzn a) | |
| Show a => Show (ISet Frzn a) | |
| Show a => Show (PureLVar Frzn a) | |
| Foldable (IMap k Frzn) | |
| Foldable (SatMap k Frzn) | As with all LVars, after freezing, map elements can be consumed. In
the case of this |
| Foldable (IMap k Frzn) | |
| (Show k, Show a) => Show (IMap k Frzn a) | |
| (Show k, Show a) => Show (SatMap k Frzn a) | |
| (Show k, Show a) => Show (IMap k Frzn a) |
An uninhabited type that signals that an LVar is not only frozen, but it may be traversed in whatever order its internal representation dictates.
Instances
| Foldable (IVar Trvrsbl) | |
| Foldable (IStructure Trvrsbl) | |
| Foldable (ISet Trvrsbl) | |
| Foldable (ISet Trvrsbl) | |
| Show a => Show (IVar Trvrsbl a) | For convenience only; the user could define this. |
| Show a => Show (IStructure Trvrsbl a) | For convenience only; the user could define this. |
| Show a => Show (ISet Trvrsbl a) | For convenience; the user could define this. |
| Show a => Show (ISet Trvrsbl a) | For convenience only; the user could define this. |
| Foldable (IMap k Trvrsbl) | |
| Foldable (SatMap k Trvrsbl) | |
| Foldable (IMap k Trvrsbl) | |
| (Show k, Show a) => Show (IMap k Trvrsbl a) | For convenience only; the user could define this. |
| (Show k, Show a) => Show (SatMap k Trvrsbl a) | For convenience only; the user could define this. |
| (Show k, Show a) => Show (IMap k Trvrsbl a) | For convenience only; the user could define this. |