fix folding, add :continue

Fix foldig to be an :acc version of in.

:continue will stop the subloop and start the next iteration of the
outer loop
This commit is contained in:
Linus Björnstam 2023-10-30 21:56:54 +01:00
parent 5668706b88
commit a47d6d992b
3 changed files with 31 additions and 18 deletions

View file

@ -30,7 +30,7 @@
;; in-stream
(define-syntax in
(syntax-rules ()
(syntax-rules (:for)
((in :for ((var) (init)) n . rest)
(n () ((var init var)) () () () . rest))
((in :for ((var) (init step)) n . rest)
@ -393,18 +393,23 @@
((var (final cursor)))
. rest))))
;; This looks wonky because it needs to reset var to the init value when the loop is re-entered
;; if it is a subloop. It does so by also binding var to folding-init in the outer binding of the current
;; loop. It has to do this because :acc clauses propagates all acc bindings to outside
;; the outermost loop.
(define-syntax folding
(syntax-rules (if :acc)
((_ :acc ((var) (init update (if guard))) n . rest)
(n ()
((var init (if guard update var)))
() ()
(syntax-rules (:acc)
((_ :acc ((var) (init update stop)) n orig name ((lets ...) . l-rest) . rest)
(n ((folding-init init))
((var folding-init update))
(stop) ()
((var var))
orig name ((lets ... (var folding-init)) . l-rest)
. rest))
((_ :acc ((var) (init update)) n . rest)
(folding :acc ((var) (init update (if #t))) n . rest))
(folding :acc ((var) (init update #f)) n . rest))
((_ :acc ((var) (init)) n . rest)
(folding :acc ((var) (init var (if #t))) n . rest))))
(folding :acc ((var) (init var #f)) n . rest))))
(define-syntax listing
(syntax-rules (:acc)