[DGD]Foreach and anonymous functions in DGD: Take 2

Felix A. Croes felix at dworkin.nl
Wed Jan 31 16:17:49 CET 2001


Lee Randolph Salzman <lsalzman+ at andrew.cmu.edu> wrote:

>[...]
> > - evaluate() doesn't seem to be checking if the object in which the
> >   anonymous function is defined still exists.
> Added code to check if the owner of the closure actually exists.
> Not quite sure if it is correct.

Not quite, you check if the object has been destructed, but not if the
object slot has been reused.  The proper check would be:

    if (owner->count != fun->elts[0].u.objcnt) {

or alternatively,

    if (DESTRUCTED(fun->elts)) {


>[...]
> >You can stick to unique function names, as long as they are
> >unique within the object, and not callable with call_other().
> >But it's better to make them private and call them with i_funcall() 
> >rather than i_call().  You can keep the current naming scheme if
> >you like, those names just wouldn't be used in calls anymore.
> Changed the specifier on a closure to C_STATIC. function_exists()
> will allow you to create a closure with the function so long as the
> creating object is actually the one on which it exists. I also
> moved to a better naming scheme for closures, essentially:
> \foo at bar where foo is the index of the closure as it occurred
> in the source file and bar is the file name in which it occurred.
> This should ensure closure names are globally unique. i_call()
> is still used as there is no real justification for duplicating
> its functionality. 
>    I was tempted to add a C_ANONYMOUS attribute to functions that
> prevents them from being the target of a call_other, but otherwise
> haves them behave as public functions so the owner could not call
> closures via a call_other, however, there seems to be no more bits
> left for this attribute. So for now, I just left closures with
> C_STATIC. A klugey solution could have been to check if the
> function's name starts with '\\', but I decided against it. :)

No more kludgy than calling "anonymous" functions by name, in the
first place.  My main reason for preferring a direct i_funcall()
using program index and function index, over i_call() using
the function's name, is that there is no name lookup required;
calling an anonymous function would be just as fast as a local
function call.  Then you can also make their class specifier
C_PRIVATE, making them uncallable by name no matter what that
name is.

This would require you to store the program index (in the object's
inheritance table) and the function index (in the program) in the
internal function array, rather than the function's name.


> >In DGD's typechecking modes 1 and 2, no return type normally means
> >`void'.
> If a closure is created with no return type, it is now assumed to have
> a return type of void.
> ex: \(){} now has an assumed return type of void.
>
> Also, just because I felt like it, I added a curry() function that
> allows you to create a new closure with implicit arguments.
> ex:
> evaluate(curry(\string(string x, string y) { return x + y; }, "foo "),
>          "bar")
> => "foo bar"
> curry() does not modify the closure passed to it but instead returns
> a new closure. curry() can be repeatedly used upon a closure and as
> expected curry (foo, bar, baz) is isomorphic to
> curry (curry (foo, bar), baz).

Shouldn't curry() check if the number of arguments is correct at currying
time?

Regards,
Dworkin

List config page:  http://list.imaginary.com/mailman/listinfo/dgd



More information about the DGD mailing list