From: Yuji Minejima
Subject: Can (loop ... collect a into var finally (return var)) be implemented by symbol-macrolet?
Date: 
Message-ID: <pan.2004.08.25.07.57.58.700330@nifty.ne.jp>
I'm touching up my loop implementation to make it produce a good expansion.
I don't have particular compilers in mind. 

Optimizing the "collect value into var" construct, I wonder if the
following expansion is valid.

(macroexpand '(loop for a in '(0 1 2) collect a into var finally (return var)))
 => (BLOCK NIL
     (LET ((#:G6823 '(0 1 2)) (A NIL))
       (LET ((#:VAR-01 (list nil)))
         (DECLARE (TYPE LIST #:VAR-01))
         (DECLARE (DYNAMIC-EXTENT #:VAR-01)) ;; !!!
         (symbol-macrolet ((var (cdr #:VAR-01))) ;; !!!
             (LET ((#:G6824 #:VAR-01))
               (DECLARE (TYPE LIST #:G6824))
               (MACROLET ((LOOP-FINISH NIL '(GO #:LOOP-EPILOGUE-6822)))
                 (TAGBODY
                    (WHEN (FUNCALL #'ENDP #:G6823) (LOOP-FINISH))
                    (SETQ A (CAR #:G6823))
                    #:LOOP-BODY-6821
                    (SETF (CDR #:G6824) (LIST A) #:G6824 (CDR #:G6824))
                    (SETQ #:G6823 (FUNCALL #'CDR #:G6823))
                    (WHEN (FUNCALL #'ENDP #:G6823) (LOOP-FINISH))
                    (PSETQ A (CAR #:G6823))
                    (GO #:LOOP-BODY-6821)
                    #:LOOP-EPILOGUE-6822
                    (RETURN-FROM NIL var))))))))
I think this can be a fairly good expansion if things go as I expected.

There are two points which can cause trouble. One is dynamic-extent
declaration (I'm content if the declaration is harmless at worst)
and the other is using symbol-macrolet for `into var'.

When symbol-macrolet is used, VAR cannot be a global variable but
is this required by the standard?

The standard says very little about the `into var' construct and you
can't do much with VAR but referering it even in the existing
implementations.


Also, I implemented the (loop ... for (a b) = (multiple-value-list (foo)))
=> (.. (multiple-value-setq (a b) (foo)) ..) optimization which was
mentioned some time ago here (destructuring is supported too).

Other loop idioms which can be optimized on the loop expansion level are
welcome.

You can see the code here.
http://homepage1.nifty.com/bmonkey/lisp/sacla/lisp/loop.lisp
This doesn't use symbol-macrolet yet, it's just an idea, but
multiple-value-list optimization is included. This code already passes all
GCL ANSI-TESTS for loop and my test code.


Thanks in advance.

Yuji.