From: hwei yin
Subject: HELP!! Curried functions (implementation)
Date: 
Message-ID: <Jun12.173440.24744@yuma.ACNS.ColoState.EDU>
Hello out there...

  We are implementing a higher order functional language.  I'm sort of stuck on
figuring out how to do Curried functions.  We're looking for some ideas or 
literature references.  I'm new at this ball game, so please be gentle if this 
question sounds stupid...

  The idea is this: we want to write functions that return function abstracts
as values.  To get the idea across, I'll write it in pseudo-LISP:

  (((lambda (A) '(lambda (B) (+ A B))) 3) 4)

The outside lambda expression, when passed 3 for A, would give us the inner
expression:

  ((lambda (B) (+ 3 B)) 4)          ; the value of A is 3: this is our problem 

This would then evaluate to 7.  I know that what was just written does not
work in LISP -- we are NOT interested in doing this in LISP; I just used LISP
to illustrate the idea so that our weird syntax won't be in the way.

Our problem is that the first evaluation comes up with:

  ((lambda (B) (+ A B)) 4)         ; the value of A is unknown -- error

When the outer lambda call is complete, its activation record is removed,
including the definition for A.  We're toying with two ideas:

(1) somehow leaving the outer activation record around so that A can be
    referenced, or

(2) partially evaluating the inner expression, replacing all A's with 3.

Neither of these sounds very appealing at the moment.

Are there any good literature references to deal with this?  Our library is
rather small, and getting literature is quite awkward.  We don't want to 
go through the trouble of sending for something that ends up not being 
helpful.  I'm sure that there are obvious and elegant ways of doing this --
I don't want to hack my way through with an ugly idea that will kill us
later on.


Thank you very much for taking the time,

   Hwei Yin (···@cs.colostate.edu)
From: Barry Margolin
Subject: Re: HELP!! Curried functions (implementation)
Date: 
Message-ID: <11aufbINNnv6@early-bird.think.com>
In article <··················@yuma.ACNS.ColoState.EDU> ···@CS.ColoState.EDU (hwei yin) writes:
>When the outer lambda call is complete, its activation record is removed,
>including the definition for A.  We're toying with two ideas:
>
>(1) somehow leaving the outer activation record around so that A can be
>    referenced, or

The problem is that you're returning a lambda expression, but you should be
returning a closure, so that the binding will be retained.  In Common Lisp
this would be:

(funcall ((lambda (a) #'(lambda (b) (+ a b))) 3) 4)

The outer lambda expression then evaluates to a closure that contains the
inner lambda expression and an environment where A is bound to 3.

>(2) partially evaluating the inner expression, replacing all A's with 3.

This is also a reasonable approach.  Presumably your compiler includes some
kind of code walker, so it should be able to find variable references and
determine whether they are to the same instance of A that is being
replaced.  You said this is a functional language, so you probably don't
even have to concern yourself with side effects, and substitution is
therefore possible; of course, if the expression is expensive to calculate,
this may result in performance problems when it is replicated.
-- 
Barry Margolin
System Manager, Thinking Machines Corp.

······@think.com          {uunet,harvard}!think!barmar