On Fri, Jun 13, 2008 at 01:14:04PM +1000, konrad Zielinski wrote:
> I've been trying to get my head around how closures work in Pico lisp.

As PicoLisp uses dynamic binding, there are no _direct_ static lexical
clausures. As in other cases too, the programmer has to (or better: can)
control things directly.

There are several functions to control dynamic environments, like 'bind'
or 'job'.

> specifically how would I set up a variable a function which returns
> successive integers each time it is called.

I would use 'job' here

   (de counter ()
      (job '((Cnt . 0))
         (inc 'Cnt) ) )

You supply a list of variables (here 'Cnt') and initial values (here
'0') to 'job', and a runtime body.

   : (counter)             
   -> 1
   : (counter)
   -> 2

If you inspect this function

   : (pp 'counter)
   (de counter NIL
      (job '((Cnt . 2)) (inc 'Cnt)) )

You see that the explicit environment is maintained by 'job'. During the
execution of the runtime body (inc 'Cnt), the variables are dynamically
bound to their values, and saved thereafter.

> My first Idea was to return this form anther function but it didn't work

You can this, too. The 'curry' function employs 'job' in certain cases

   (de make-counter (InitialValue @Increment)
      (curry (@Increment InitialValue) ()
         (inc 'InitialValue @Increment) ) )

Calling 'make-counter' returns a new function

   : (make-counter 0 1)                        
   -> (NIL (job '((InitialValue . 0)) (inc 'InitialValue 1)))

which is basically the same as our counter above.

   : (def 'counter (make-counter 0 1))
   -> counter
   : (counter)                        
   -> 1
   : (counter)
   -> 2

- Alex

Reply via email to