From 253da1e9f50bb1a3497b5bd3e39f6a10233ec6ad Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Suzanne=20Dup=C3=A9ron?= Date: Sat, 28 Mar 2020 22:28:28 +0100 Subject: [PATCH] Break down the large fold_config structure into smaller structures --- src/stages/adt_generator/generator.raku | 66 +++++++++++++++---------- src/test/adt_generator/use_a_fold.ml | 13 ++--- 2 files changed, 47 insertions(+), 32 deletions(-) diff --git a/src/stages/adt_generator/generator.raku b/src/stages/adt_generator/generator.raku index 6430e0773..193cf291d 100644 --- a/src/stages/adt_generator/generator.raku +++ b/src/stages/adt_generator/generator.raku @@ -172,25 +172,35 @@ for $adts.kv -> $index, $t { } say ""; -say "type 'state continue_fold_map ="; -say ' {'; for $adts.list -> $t { - say " $t : $t -> 'state -> ($t * 'state) ;"; + say "type 'state continue_fold_map__$t = \{"; + say " node__$t : $t -> 'state -> ($t * 'state) ;"; for $t.list -> $c { say " $t__$c : {$c || 'unit'} -> 'state -> ({$c || 'unit'} * 'state) ;" } + say ' }'; +} + +say "type 'state continue_fold_map = \{"; +for $adts.list -> $t { + say " $t : 'state continue_fold_map__$t ;"; } say ' }'; say ""; +for $adts.list -> $t +{ say "type 'state fold_map_config__$t = \{"; + say " node__$t : $t -> (*Adt_info.node_instance_info ->*) 'state -> ('state continue_fold_map) -> ($t * 'state) ;"; + say " node__$t__pre_state : $t -> (*Adt_info.node_instance_info ->*) 'state -> 'state ;"; + say " node__$t__post_state : $t -> $t -> (*Adt_info.node_instance_info ->*) 'state -> 'state ;"; + for $t.list -> $c + { say " $t__$c : {$c || 'unit'} -> (*Adt_info.ctor_or_field_instance_info ->*) 'state -> ('state continue_fold_map) -> ({$c || 'unit'} * 'state) ;"; + } + say '}' } + say "type 'state fold_map_config ="; say ' {'; for $adts.list -> $t -{ say " $t : $t -> (*Adt_info.node_instance_info ->*) 'state -> ('state continue_fold_map) -> ($t * 'state) ;"; - say " $t__pre_state : $t -> (*Adt_info.node_instance_info ->*) 'state -> 'state ;"; - say " $t__post_state : $t -> $t -> (*Adt_info.node_instance_info ->*) 'state -> 'state ;"; - for $t.list -> $c - { say " $t__$c : {$c || 'unit'} -> (*Adt_info.ctor_or_field_instance_info ->*) 'state -> ('state continue_fold_map) -> ({$c || 'unit'} * 'state) ;"; - } } +{ say " $t : 'state fold_map_config__$t;" } say ' }'; say ""; @@ -295,9 +305,11 @@ say '(* Curries the "visitor" argument to the folds (non-customizable traversal say "and mk_continue_fold_map : type qstate . qstate fold_map_config -> qstate continue_fold_map = fun visitor ->"; say ' {'; for $adts.list -> $t -{ say " $t = fold_map__$t visitor ;"; +{ say " $t = \{"; + say " node__$t = fold_map__$t visitor ;"; for $t.list -> $c - { say " $t__$c = fold_map__$t__$c visitor ;"; } } + { say " $t__$c = fold_map__$t__$c visitor ;"; } + say ' };' } say ' }'; say ""; @@ -306,15 +318,15 @@ say ""; for $adts.list -> $t { say "and fold_map__$t : type qstate . qstate fold_map_config -> $t -> qstate -> ($t * qstate) = fun visitor x state ->"; say " let continue_fold_map : qstate continue_fold_map = mk_continue_fold_map visitor in"; - say " let state = visitor.$t__pre_state x (*(fun () -> whole_adt_info, info__$t)*) state in"; - say " let (new_x, state) = visitor.$t x (*(fun () -> whole_adt_info, info__$t)*) state continue_fold_map in"; - say " let state = visitor.$t__post_state x new_x (*(fun () -> whole_adt_info, info__$t)*) state in"; + say " let state = visitor.$t.node__$t__pre_state x (*(fun () -> whole_adt_info, info__$t)*) state in"; + say " let (new_x, state) = visitor.$t.node__$t x (*(fun () -> whole_adt_info, info__$t)*) state continue_fold_map in"; + say " let state = visitor.$t.node__$t__post_state x new_x (*(fun () -> whole_adt_info, info__$t)*) state in"; say " (new_x, state)"; say ""; for $t.list -> $c { say "and fold_map__$t__$c : type qstate . qstate fold_map_config -> { $c || 'unit' } -> qstate -> ({ $c || 'unit' } * qstate) = fun visitor x state ->"; say " let continue_fold_map : qstate continue_fold_map = mk_continue_fold_map visitor in"; - say " visitor.$t__$c x (*(fun () -> whole_adt_info, info__$t, info__$t__$c)*) state continue_fold_map"; + say " visitor.$t.$t__$c x (*(fun () -> whole_adt_info, info__$t, info__$t__$c)*) state continue_fold_map"; say ""; } } @@ -327,7 +339,7 @@ for $adts.list -> $t say " adt = whole_adt_info () ;"; say " node_instance = continue_info__$t visitor x"; say ' } in'; - # say " let (new_x, state) = visitor.$t x (fun () -> whole_adt_info, info__$t) state continue_fold in"; + # say " let (new_x, state) = visitor.$t.node__$t x (fun () -> whole_adt_info, info__$t) state continue_fold in"; say " visitor.generic node_instance_info state"; say ""; for $t.list -> $c @@ -341,44 +353,46 @@ for $adts.list -> $t say " let state = (*visitor.generic_ctor_or_field ctor_or_field_instance_info*) fold__$c visitor x state in"; } say " state"; - # say " visitor.$t__$c x (fun () -> whole_adt_info, info__$t, info__$t__$c) state continue_fold"; + # say " visitor.$t.$t__$c x (fun () -> whole_adt_info, info__$t, info__$t__$c) state continue_fold"; say ""; } } say "let no_op : 'a fold_map_config = \{"; for $adts.list -> $t -{ say " $t = (fun v (*_info*) state continue ->"; +{ say " $t = \{"; + say " node__$t = (fun v (*_info*) state continue ->"; say " match v with"; if ($t eq $variant) { for $t.list -> $c { given $c { - when '' { say " | $c -> let ((), state) = continue.$t__$c () state in ($c, state)"; } - default { say " | $c v -> let (v, state) = continue.$t__$c v state in ($c v, state)"; } } } + when '' { say " | $c -> let ((), state) = continue.$t.$t__$c () state in ($c, state)"; } + default { say " | $c v -> let (v, state) = continue.$t.$t__$c v state in ($c v, state)"; } } } } elsif ($t eq $record) { print ' { '; for $t.list -> $f { print "$f; "; } say "} ->"; for $t.list -> $f - { say " let ($f, state) = continue.$t__$f $f state in"; } + { say " let ($f, state) = continue.$t.$t__$f $f state in"; } print ' ({ '; for $t.list -> $f { print "$f; "; } say '}, state)'; } else { print " v -> fold_map__$t v state ( "; - print ( "continue.$t__$_" for $t.list ).join(", "); + print ( "continue.$t.$t__$_" for $t.list ).join(", "); say " )"; } say " );"; - say " $t__pre_state = (fun v (*_info*) state -> ignore v; state) ;"; - say " $t__post_state = (fun v new_v (*_info*) state -> ignore (v, new_v); state) ;"; + say " node__$t__pre_state = (fun v (*_info*) state -> ignore v; state) ;"; + say " node__$t__post_state = (fun v new_v (*_info*) state -> ignore (v, new_v); state) ;"; for $t.list -> $c { print " $t__$c = (fun v (*_info*) state continue -> "; if ($c) { print "ignore continue; (v, state)"; } else { - print "continue.$c v state"; + print "continue.$c.node__$c v state"; } - say ") ;"; } } + say ") ;"; } + say ' };' } say '}'; diff --git a/src/test/adt_generator/use_a_fold.ml b/src/test/adt_generator/use_a_fold.ml index 8774e1200..5591d87cf 100644 --- a/src/test/adt_generator/use_a_fold.ml +++ b/src/test/adt_generator/use_a_fold.ml @@ -7,10 +7,11 @@ let () = let some_root : root = A [{ a1 = X (A [{ a1 = X (B [1;2;3]) ; a2 = W () ; }]) ; a2 = Z (W ()) ; }] in let op = { no_op with - a = fun the_a (*_info*) state continue_fold -> - let (a1__' , state') = continue_fold.ta1 the_a.a1 state in - let (a2__' , state'') = continue_fold.ta2 the_a.a2 state' in - ({ a1__' ; a2__' }, state'' + 1) + a = { no_op.a with + node__a = fun the_a (*_info*) state continue_fold -> + let (a1__' , state') = continue_fold.ta1.node__ta1 the_a.a1 state in + let (a2__' , state'') = continue_fold.ta2.node__ta2 the_a.a2 state' in + ({ a1__' ; a2__' }, state'' + 1) } } in let state = 0 in let (_, state) = fold_map__root op some_root state in @@ -21,7 +22,7 @@ let () = let () = let some_root : root = A [{ a1 = X (A [{ a1 = X (B [1;2;3]) ; a2 = W () ; }]) ; a2 = Z (W ()) ; }] in - let op = { no_op with a__pre_state = fun _the_a (*_info*) state -> state + 1 } in + let op = { no_op with a = { no_op.a with node__a__pre_state = fun _the_a (*_info*) state -> state + 1 } } in let state = 0 in let (_, state) = fold_map__root op some_root state in if state != 2 then @@ -31,7 +32,7 @@ let () = let () = let some_root : root = A [{ a1 = X (A [{ a1 = X (B [1;2;3]) ; a2 = W () ; }]) ; a2 = Z (W ()) ; }] in - let op = { no_op with a__post_state = fun _the_a _new_a (*_info*) state -> state + 1 } in + let op = { no_op with a = { no_op.a with node__a__post_state = fun _the_a _new_a (*_info*) state -> state + 1 } } in let state = 0 in let (_, state) = fold_map__root op some_root state in if state != 2 then