[parenscript-devel] Should implicit return in PS mean always explicitly returning null in JS?

Daniel Gackle danielgackle at gmail.com
Fri Dec 4 20:02:27 UTC 2009


Hi Wout,

Oops, I thought I had stripped all of the app-specific code out of that
function, but I hadn't. Here's another try:

(defun blep (ss x y)
  (when foo?
    (let ((pair (bar)))
      (unless (null pair)
        (destructuring-bind (a b) pair
          (unless (or (null a) (null b))
            (let ((val (baz a b)))
              (unless (null val)
                (when (blah val)
                  (unless (blee)
                    t))))))))))

(The point is that this is the skeleton of an actual function from our
program. It's been macroexpanded in a few places and had the names changed.)

To answer your questions: (1) your PS version is prior to Vladimir's work on
implicit RETURN, which is why your generated code is so different from what
I posted; (2) yes, there is a PS version of DESTRUCTURING-BIND. It's not the
full CL version, though. If you discover you want something it doesn't do
yet, post to this list. A lot of what's missing will be fairly easy to add.
(And while you're at it, check out PS's LOOP as well. It too doesn't do
everything that CL's does, but it does a surprising amount.)

Daniel


On Fri, Dec 4, 2009 at 7:44 AM, Wout Perquin <wout.perquin at skynet.be> wrote:

> On Thu, 2009-12-03 at 17:10 -0800, Red Daly wrote:
> > On Thu, Dec 3, 2009 at 1:41 PM, Daniel Gackle <danielgackle at gmail.com>
> wrote:
> > > I've now had a chance to systematically look at how our code fares
> under
> > > PS's implicit return. Thanks to Scott for being the guinea pig for the
> rest
> > > of us. I like it! I do have a few questions/issues. I'll send them in
> > > separate emails, I guess.
> > >
> > > PS now tries to insert a default "return null;" statement in functions
> that
> > > would formerly have returned nothing, i.e. whose return values would
> have
> > > been undefined. I am not convinced that this buys us much. We've always
> > > treated NULL and UNDEFINED as conveying the same information when
> returning
> > > from a function. I recognize not everyone would share this
> interpretation.
> > >
> > > The trouble with explicit "return null" is that you end up with things
> like
> > > the following example taken from our code (stripped-down for brevity):
> > >
> > > (defun blep (ss x y)
> > >       (when foo?
> > >         (awhen (bar)
> > >           (destructuring-bind (c r) it
> > >             (when (!null c r)
> > >               (awhen (baz)
> > >                 (when (blah it)
> > >                   (unless (blee)
> > >                     t))))))))
> > >
> > > =>
> > >
> I try to follow this conversation, but above (defun blep [...]) on my
> system returns :
> "function blep(ss, x, y) {
>    if (foowhat) {
>         awhen(bar(), destructuringBind(c(r), it, bangnull(c, r) ?
> awhen(baz(), blah(it) ? (!blee() ? true : null) : null) : null));
>    };
> };" ; I used (ps:ps ...)
> I assume that is because I either run the wrong Parenscript version or
> there are macros involved that I don't have.
> ps, it got my attention because of destructering-bind, is that a macro
> in the latest Parenscript release ?
> Thanks, Wout
> >
> > > function blep(ss, x, y) {
> > >     if (foowhat) {
> > >         var it = bar();
> > >         if (it != null && it !== false) {
> > >             var c = it[0];
> > >             var r = it[1];
> > >             if (c != null && r != null) {
> > >                 var it27537 = baz();
> > >                 if (it27537 != null && it27537 !== false) {
> > >                     if (blah(it27537)) {
> > >                         if (!blee()) {
> > >                             return true;
> > >                         } else {
> > >                             return null;
> > >                         };
> > >                     } else {
> > >                         return null;
> > >                     };
> > >                 } else {
> > >                     return null;
> > >                 };
> > >             } else {
> > >                 return null;
> > >             };
> > >         } else {
> > >             return null;
> > >         };
> > >     } else {
> > >         return null;
> > >     };
> > > };
> >
> > For this specific example it's more a matter of generating reasonable
> > code.  There is a better way to represent this function, even when
> > implicitly returning null:
> >
> > function blep(ss, x, y) {
> >     var expr = null;
> >     if (foowhat) {
> >         var it = bar();
> >         if (it != null && it !== false) {
> >             var c = it[0];
> >             var r = it[1];
> >             if (c != null && r != null) {
> >                 var it27537 = baz();
> >                 if (it27537 != null && it27537 !== false) {
> >                     if (blah(it27537)) {
> >                         if (!blee()) {
> >                             expr = true;
> >                         }
> >                     }
> >                 }
> >             }
> >         }
> >     }
> >     return expr;
> > };
> >
> > Now if I am not mistaken, Parenscript cannot make (or fake) an
> > expression from any old Parenscript form.  In my mind this is a
> > shortcoming of Parenscript, not something we should embrace because
> > Javascript distinguishes between statements and expressions.  If I am
> > wrong, then I'd be glad to hear about it!
> >
> > If we had a 100% working parenscript-form => javascript expression
> > implementation, then implementing implicit returning would be simpler
> > and this code generation.  I have not seen the implicit return code,
> > but this behavior may require more extensive semantic analysis than
> > Parenscript currently supports.
> >
> > >
> > > I wish PS would avoid generating all those "return null"s when the only
> > > thing we need is the "return true".
> > >
> > > Note also that PS is not *always* returning null; there are cases where
> the
> > > old undefined behavior still exists:
> > >
> > > (ps (defun foo () (dolist (a b) (blah a))))
> > > =>
> > > "function foo() {
> > >     for (var a = null, _js_idx27540 = 0; _js_idx27540 < b.length;
> > > _js_idx27540 += 1) {
> > >         a = b[_js_idx27540];
> > >         blah(a);
> > >     };
> > > };"
> > >
> > > Personally, I think this is fine and would rather see all functions
> behave
> > > this way. That is, if I put a NIL in a tail position in my code, I
> should
> > > get "return null" and otherwise no explicit return in JS. We can't
> factor
> > > the null vs. undefined distinction out of PS altogether; it's too
> engrained
> > > in JS. Anyway this issue is, to my mind, distinct from the implicit
> return
> > > feature as such.
> >
> > For most cases it will not make any difference.  If it is important to
> > the application, you can always explicitly return ps:undefined or nil.
> >
> > Red
> >
> > >
> > > What am I missing?
> > >
> > > Daniel
> > >
> > > _______________________________________________
> > > parenscript-devel mailing list
> > > parenscript-devel at common-lisp.net
> > > http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel
> > >
> > >
> >
> > _______________________________________________
> > parenscript-devel mailing list
> > parenscript-devel at common-lisp.net
> > http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel
>
>
> _______________________________________________
> parenscript-devel mailing list
> parenscript-devel at common-lisp.net
> http://common-lisp.net/cgi-bin/mailman/listinfo/parenscript-devel
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mailman.common-lisp.net/pipermail/parenscript-devel/attachments/20091204/407b99d4/attachment.html>


More information about the parenscript-devel mailing list