diff options
author | Kaz Kylheku <kaz@kylheku.com> | 2018-03-21 06:20:32 -0700 |
---|---|---|
committer | Kaz Kylheku <kaz@kylheku.com> | 2018-03-21 06:20:32 -0700 |
commit | 20ed2b83c35baa623882e1b1f2bce37ecbfdb21c (patch) | |
tree | f912167c9cd399b8ae1641f8851ea4270d1071b0 | |
parent | aeaa830b0b2221b54fe09e6b6c93558cb3384d26 (diff) | |
download | txr-20ed2b83c35baa623882e1b1f2bce37ecbfdb21c.tar.gz txr-20ed2b83c35baa623882e1b1f2bce37ecbfdb21c.tar.bz2 txr-20ed2b83c35baa623882e1b1f2bce37ecbfdb21c.zip |
compiler: handle sys:each-op special form.
* share/txr/stdlib/compiler.tl (compiler compile): Handle
sys:each-op with help of expand-each.
(expand-each): New function.
-rw-r--r-- | share/txr/stdlib/compiler.tl | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/share/txr/stdlib/compiler.tl b/share/txr/stdlib/compiler.tl index ad6d886f..5fc71dfc 100644 --- a/share/txr/stdlib/compiler.tl +++ b/share/txr/stdlib/compiler.tl @@ -150,6 +150,7 @@ ((let let*) me.(comp-let oreg env form)) (lambda me.(comp-lambda oreg env form)) (sys:for-op me.(comp-for oreg env form)) + (sys:each-op me.(compile oreg env (expand-each form env))) (progn me.(comp-progn oreg env (cdr form))) (and me.(comp-and-or oreg env form)) (or me.(comp-and-or oreg env form)) @@ -643,6 +644,26 @@ (sys:setq ,val-var (cdr ,cell-var)) ,*body))))) +(defun expand-each (form env) + (mac-param-bind form (op each-type vars . body) form + (unless vars + (set vars [mapcar car env.vb])) + (let* ((gens (mapcar (ret (gensym)) vars)) + (out (if (member each-type '(collect-each append-each)) + (gensym))) + (accum (if out (gensym)))) + ^(let* (,*(zip gens vars) ,*(if accum ^((,out (cons nil nil)) (,accum ,out)))) + (sys:for-op () + ((and ,*gens) ,*(if accum ^((cdr ,out)))) + (,*(mapcar (ret ^(sys:setq ,@1 (cdr ,@1))) gens)) + ,*(mapcar (ret ^(sys:setq ,@1 (car ,@2))) vars gens) + ,*(caseq each-type + (collect-each ^((rplacd ,accum (cons (progn ,*body) nil)) + (sys:setq ,accum (cdr ,accum)))) + (append-each ^((rplacd ,accum (progn ,*body)) + (sys:setq ,accum (last ,accum)))) + (t body))))))) + (defun usr:compile-toplevel (exp) (let ((co (new compiler)) (as (new assembler))) |