Library
Module
Module type
Parameter
Class
Class type
A simple library for parallel incremental computations. Based on "Efficient Parallel Self-Adjusting Computation".
Var.t
with certain values.Var.watch
operation on Var.t
and change it to incremental
.incremental
signifies a computation in itself.incremental
s and make even bigger incremental
s.incremental
by running it (a run
operation is provided by the library).'a incremental
returns a 'a computation
.Var.t
(done with Var.set
operation), it marks all dependent computations dirty.propagate
operation on a dirty computation
updates its value efficiently.destroy_comp
operation) computation
when its no more required.A 'a t
holds a value of type 'a
. This type is opaque and we don't expose any mechanism to change this or modify it. Computations happens by chaining together various combinators provided by the library, all of which operate on 'a t
.
type 'a incremental := 'a t
Type 'a incremental
is an alias for 'a t
.
An executor
is something that has to be passed while initially running the computation. The reason behind this is, we want to support multiple ways to run computations in parallel and library users can use the one that is best for them.
Suppose you have your own scheduler built on top of Domains
and you don't want to use Domainslib for running tasks. You can very well use it as long as you provide these two run
and par_do
functions.
If however you want to use Domainslib
, you would have an executor
which would look roughly like this:
module T = Domainslib.Task
let pool = T.setup_pool ~num_domains:(Domain.recommended_domain_count () / 2) ()
let par_runner f = T.run pool f
let par_do l r =
let lres = T.async pool l in
let rres = r () in
(T.await pool lres, rres)
let executor = {run = par_runner; par_do}
module Cutoff : sig ... end
module Var : sig ... end
Defines the type and various operations for modifiable values.
val return : 'a -> 'a t
return x
returns an instance of 'a incremental
from x
of type 'a
.
map ~fn a
maps the internal value of a
to fn
. Default cutoff
is Phys_equal
.
combine a b
is useful function to combine two incremental
's into one.
bind ~fn a
calls fn
with the value of a
and returns that. This lets us build computations that are more dynamic in nature. This is the monadic bind operation for incremental
s.
val value : 'a computation -> 'a
value c
returns the value/result associated with the computation c
.
val run : executor:executor -> 'a t -> 'a computation
run ~executor t
evaluates t
with the provided executor
. This stores the result of the computation as well as all the data structures associated with it.
val propagate : 'a computation -> unit
propagate c
will propagate the changes to all the Var.t
that the computation c
depended on. If there are no changes, it will not do any extra work and returns back right away.
val dump_tree : string -> 'a computation -> unit
dump_tree file c
will dump the computation tree associated with c
into file
. It dumps the tree in D2 format. See the instructions for viewing the files.
val destroy_comp : 'a computation -> unit
destroy_comp c
will destroy the computation associated with c
. After destroying, calling propagate
on c
will result in an exception. It's necessary to destroy computations that are no longer needed. A computation will be taking up memory and doing unnecessary work if not destroyed.
module Debug : sig ... end