XLISP > XLISP 2.0  -  Contents  -  Reference  -  Previous | Next


Type:   -   special form (fsubr)
Source:   -   xlcont.c


(do* ([binding ... ]) (test-expr [result]) [expr ... ])
binding - a variable binding which is can take one of the following forms:
(symbol init-expr [step-expr])
symbol - a symbol
init-expr - an initialization expression for symbol
step-expr - an expression with that symbol is updated at the end of each loop
test-expr - iteration ends when this expression returns a non-NIL value
result - an optional expression for the returned result
expr - expressions comprising the body of the loop which may contain returns, gos or tags for go
returns - the value of the last result expression


The 'do*' special form is basically a 'while' looping construct that contains symbols [with optional initializations and updates], a loop test [with an optional return value] and a block of code [expressions] to evaluate. The 'do*' form evaluates its initializations and updates in sequential order [as opposed to do which doesn't]. The sequence of these events is:

  init-expr execution
  while test-expr do
    loop code execution
    step-expr execution
  return result

The first form after the 'do*' is the 'binding' form. It contains a series of 'symbols' or 'bindings'. The 'binding' is a 'symbol' followed by an initialization expression 'init-expr' and an optional 'step-expr'. If there is no 'init-expr', the 'symbol' will be initialized to NIL. There is no specification as to the order of execution of the bindings or the step expressions, except that they happen all together.

The 'do*' form will go through and create and initialize the symbols. This is followed by evaluating the 'test-expr'. If 'test-expr' returns a non-NIL value, the loop will terminate. If 'test-expr' returns a NIL value then the 'do*' will sequentially execute the 'exprs'. After execution of the loop 'exprs', the 'symbols' are set to the step-exprs' [if the 'step-exprs' exist]. Then, the 'test-expr' is re-evaluated, and so on. The value of the 'result' expression is evaluated and returned. If no 'result' is specified, NIL is returned. When the 'do*' is finished execution, the 'symbols' that were defined will no longer exist or retain their values.


(do                                 ; DO example - won't work
  ((i 0)                            ;   var I=0
   (j i))                           ;   var J=I (won't work)
  ((eql i j) "done")                ;   test and result
  (print "looping"))                ; error: unbound variable - I

(do*                                ; DO* example - will work
  ((i 0)                            ;   var I=0
   (j i))                           ;   var J=I (proper exec. order)
  ((eql i j) "done")                ;   test and result
  (print "looping"))                ;   returns "done"

(do* (i)                            ; DO* loop with var I
  ((eql i 0) "done")                ;   test and result
  (print i) (setq i 0) (print i))   ;   prints NIL 0
                                    ;   returns "done"

(do* (i)                            ; DO* loop with var I
  ((eql i 0))                       ;   test but no result
  (print i) (setq i 0) (print i))   ;   prints NIL 0
                                    ;   returns NIL

(do*                                ; DO* loop
  ((i 0 (setq i (1+ i)))            ;   var I=0  increment by 1
   (j 10 (setq j (1- j))))          ;   var J=10 decrement by 1
  ((eql i j)  "met in the middle")  ;   test and result
  (princ i) (princ " ")             ;   prints  0 10
  (princ j) (terpri))               ;           1 9
                                    ;           2 8
                                    ;           3 7
                                    ;           4 6
                                    ;   returns "met in the middle"

See the do* special form in the XLISP 2.0 manual.

  Back to Top

XLISP > XLISP 2.0  -  Contents  -  Reference  -  Previous | Next