src/Pure/General/lazy.ML
changeset 29422 fdf396a24a9f
parent 28971 300ec36a19af
child 32738 15bb09ca0378
equal deleted inserted replaced
29421:db532e37cda2 29422:fdf396a24a9f
     1 (*  Title:      Pure/General/lazy.ML
     1 (*  Title:      Pure/General/lazy.ML
     2     ID:         $Id$
       
     3     Author:     Florian Haftmann and Makarius, TU Muenchen
     2     Author:     Florian Haftmann and Makarius, TU Muenchen
     4 
     3 
     5 Lazy evaluation with memoing.  Concurrency may lead to multiple
     4 Lazy evaluation with memoing.  Concurrency may lead to multiple
     6 attempts of evaluation -- the first result persists.
     5 attempts of evaluation -- the first result persists.
     7 *)
     6 *)
    11   type 'a lazy
    10   type 'a lazy
    12   val same: 'a lazy * 'a lazy -> bool
    11   val same: 'a lazy * 'a lazy -> bool
    13   val lazy: (unit -> 'a) -> 'a lazy
    12   val lazy: (unit -> 'a) -> 'a lazy
    14   val value: 'a -> 'a lazy
    13   val value: 'a -> 'a lazy
    15   val peek: 'a lazy -> 'a Exn.result option
    14   val peek: 'a lazy -> 'a Exn.result option
       
    15   val force_result: 'a lazy -> 'a Exn.result
    16   val force: 'a lazy -> 'a
    16   val force: 'a lazy -> 'a
    17   val map_force: ('a -> 'a) -> 'a lazy -> 'a lazy
    17   val map_force: ('a -> 'a) -> 'a lazy -> 'a lazy
    18 end
    18 end
    19 
    19 
    20 structure Lazy :> LAZY =
    20 structure Lazy :> LAZY =
    39   | Result res => SOME res);
    39   | Result res => SOME res);
    40 
    40 
    41 
    41 
    42 (* force result *)
    42 (* force result *)
    43 
    43 
    44 fun force r =
    44 fun force_result r =
    45   let
    45   let
    46     (*potentially concurrent evaluation*)
    46     (*potentially concurrent evaluation*)
    47     val res =
    47     val res =
    48       (case ! r of
    48       (case ! r of
    49         Lazy e => Exn.capture e ()
    49         Lazy e => Exn.capture e ()
    51     (*assign result -- first one persists*)
    51     (*assign result -- first one persists*)
    52     val res' = NAMED_CRITICAL "lazy" (fn () =>
    52     val res' = NAMED_CRITICAL "lazy" (fn () =>
    53       (case ! r of
    53       (case ! r of
    54         Lazy _ => (r := Result res; res)
    54         Lazy _ => (r := Result res; res)
    55       | Result res' => res'));
    55       | Result res' => res'));
    56   in Exn.release res' end;
    56   in res' end;
       
    57 
       
    58 fun force r = Exn.release (force_result r);
    57 
    59 
    58 fun map_force f = value o f o force;
    60 fun map_force f = value o f o force;
    59 
    61 
    60 end;
    62 end;
    61 
    63