From: David Sletten Date: 2005-02-02T18:50:46+09:00 Subject: Re: Partial function application (was: Re: Binding precedence for first sym...) E S wrote: > > > Oh, I was serious. Partial function application (also referred to as > 'macro binding' and 'currying') means that given a certain function > (or method), e.g. > > def fun(x, y, z) > q = x + y + z > end > > If this function is invoked with a partial argument list, e.g. > > fun 1, 2 > > Then, instead of throwing some sort of an error, the call would > produce a new function where the given arguments are bound. > Essentially, the previous call would yield: > > def fun(z) > q = 1 + 2 + z > end > > So these calls would be equal: > > fun(1, 2, 3) # => 6 > ((fun 1, 2) 3) # => 6 > fun(1, 2)(3) # => 6 > x = fun(1, 2); x(3) # => 6 > > The only problem would be handling the destructive updates, i.e. what > would happen if one tried to curry this with x: > > def fun(x, y, z) > x = x + y + z > end > > x can't be directly substituted since it's assigned to. It'd have to > be translated to 'xx = x + y + z' or something. > > This probably isn't something most Rubyists, at least initially, would > be excited about but it's quite useful. I think it'd be possible to > implement as a library but it'd obviously be fairly slow. Of course > there's always Haskell :) > This isn't exactly what you were asking for, but it fills some of the gap. It's a fairly straightforward (i.e., ripped off from) translation of an example by Paul Graham in _ANSI_Common_Lisp_ (pg. 110). He was attempting to simulate a similar feature from Dylan. def curry(f, *args) lambda {|*args2| f.call(*(args + args2))} end fun = lambda {|x, y, z| x + y + z} fun.call(1, 2, 3) => 6 f1 = curry(fun, 1) f1.call(2, 3) => 6 f2 = curry(fun, 1, 2) f2.call(3) => 6 I'm fairly new to Ruby, but I think this is the right way to do this. David Sletten