Ah! Very good points, thank you for the explanation. _Nick_
On Thu, Aug 5, 2010 at 2:13 PM, Daniel Gackle <[email protected]>wrote: > < why not just use an object as the only parameter > > > That was the first way we did it, and we changed it for a good reason, > but my recollection of why is fuzzy. Does anybody remember? > The archives of this list may be helpful here. > > I believe the reason may have been that it places an undue burden > on the caller. If I want to write something like this... > > (member item arr :key foo :test bar) > > ... who is going to figure out that the last 4 arguments are really two > keyword params and bundle them into { key : foo, test : bar }? > > You could make the caller do it: > > (member item arr (create :key foo :test bar)) > > ... but then you lose interoperability with CL, and arguably dilute the > feature to the point where you might as well not have it, since it's > easy enough to define a function that takes a js object as its last > parameter and picks out the keys. > > On the other hand, you could make PS do it by decreeing that > keywords in an arglist *always* identify keyword params, but > that breaks this: > > (member :blah arr :key foo :test bar) > > ... which now generates member({blah : arr, key : foo, test : bar}) > instead of the desired member("blah", arr, {key : foo, test : bar}). > In other words, this option makes the semantics of keywords > inconsistent in PS. > > Another option is to make the PS compiler consider the signature > of the function being called before it generates the code for the call. > That complicates the compiler and IIRC is hard to get working in > the general case (Vladimir can comment here). > > So my recollection is that we settled on the existing method as the > one that places no burden on either the caller or the callee (at the source > level... obviously the JS that's generated for the callee is what does > all the extra work), preserves the semantics of keywords, is closest > to how CL does keyword args, and keeps the compiler simple. > > > > > On Thu, Aug 5, 2010 at 2:47 PM, Nick Fitzgerald <[email protected]> wrote: > >> Ok, I just realized that I completely misread your original post. I >> thought you were proposing the removal of defaulting to null rather than >> leaving the value undefined. >> >> Have you done any profiling to see if there is a reasonable difference >> between >> >> "function foo() { >> var a; >> // ... pick out and assign keyword args ... >> if (a === undefined) { >> a = null; >> }; >> return bar(a); >> };" >> >> and >> >> "function foo() { >> var a = null; >> // ... pick out and assign keyword args ... >> return bar(a); >> };" >> >> ? >> >> I just ran this very naive test in Chromium: >> >> var then = +new Date; >> var i = 20000; >> while (i--) { >> (function () { >> var a; >> if (a === undefined) a = null; >> }()) >> }; >> console.log(+new Date - then); >> >> Which logs 70 ms. >> >> var then = +new Date; >> var i = 20000; >> while (i--) { >> (function () { >> var a = null; >> }()) >> }; >> console.log(+new Date - then); >> >> >> This one logs 71 ms. >> >> This has to have come up before, but why not just use an object as the >> only parameter and use it's keys as the keyword arguments? I just ran the >> same test for that, and when the keyword was missing I got 82 ms, but when >> it was available, I got 56. >> >> I think using objects would make the generated code much more readable, >> which trumps speed in this case IMO given that the difference is so small >> and the high number of iterations being performed. >> >> _Nick_ >> >> >> >> >> On Thu, Aug 5, 2010 at 1:24 PM, Daniel Gackle <[email protected]>wrote: >> >>> Good point. I kept the null assignment for consistency with how PS does >>> &optional >>> arguments. But this begs the question: why do we care about &optional >>> and &key arguments being set to null, as opposed to just leaving them >>> undefined? >>> I'm trying to remember the reason... anybody? >>> >>> Our experience has been that PS code works best if one treats null and >>> undefined >>> as interchangeable. But that may be an artifact of running some of the >>> same code >>> in CL as well, where there is no such distinction. >>> >>> >>> On Thu, Aug 5, 2010 at 1:51 PM, Nick Fitzgerald <[email protected]>wrote: >>> >>>> +1 from me but that doesn't mean too much. >>>> >>>> No need to explicitly set them as `null`, because JS already has (the >>>> more semantic in this case) `undefined`. >>>> >>>> _Nick_ >>>> >>>> >>>> >>>> On Wed, Aug 4, 2010 at 12:30 PM, Daniel Gackle >>>> <[email protected]>wrote: >>>> >>>>> The code that's generated for a keyword argument goes like this: >>>>> >>>>> (ps (defun foo (&key a) (bar a))) => >>>>> >>>>> (abbreviated for clarity): >>>>> >>>>> "function foo() { >>>>> var a; >>>>> // ... pick out and assign keyword args ... >>>>> if (a === undefined) { >>>>> a = null; >>>>> }; >>>>> return bar(a); >>>>> };" >>>>> >>>>> It seems to me that this could be made tighter as follows: >>>>> >>>>> "function foo() { >>>>> var a = null; >>>>> // ... pick out and assign keyword args ... >>>>> return bar(a); >>>>> };" >>>>> >>>>> The only difference I can think of is when someone explicitly passes >>>>> undefined >>>>> as a value for the argument, but that's an oxymoronic thing to do. >>>>> >>>>> Can anyone think of a reason not to make this change? I like PS's >>>>> keyword >>>>> arguments a lot, but the generated JS is bloated enough to make me >>>>> wince. >>>>> >>>>> _______________________________________________ >>>>> parenscript-devel mailing list >>>>> [email protected] >>>>> http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel >>>>> >>>>> >>>> >>>> _______________________________________________ >>>> parenscript-devel mailing list >>>> [email protected] >>>> http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel >>>> >>>> >>> >>> _______________________________________________ >>> parenscript-devel mailing list >>> [email protected] >>> http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel >>> >>> >> >> _______________________________________________ >> parenscript-devel mailing list >> [email protected] >> http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel >> >> > > _______________________________________________ > parenscript-devel mailing list > [email protected] > http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel > >
_______________________________________________ parenscript-devel mailing list [email protected] http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel
