musictheory / NilScript

Objective-C-style language superset of JavaScript with a tiny, simple runtime
Other
50 stars 5 forks source link

Generate optional chains #168

Open iccir opened 1 year ago

iccir commented 1 year ago

Currently, we need to use temporary variables to store the result of each message. For example:

[[[anObject foo] bar] baz]

becomes:

var N$_t_0,N$_t_1;
((N$_t_0 = (((N$_t_1 = ((anObject && anObject.N$_f_foo())))
    && N$_t_1.N$_f_bar()))) && N$_t_0.N$_f_baz());

Using optional chaining, we can eliminate these temporary variables:

anObject?.N$_f_foo()?.N$_f_bar()?.N$_f_baz()

Unfortunately, optional chaining returns undefined rather than null when it short-circuits. During implicit conversions, undefined becomes NaN rather than 0. Hence, the following:

[anObject foo] + 5

will now be NaN if anObject is null.

We can use nullish coalescing to ensure that messaging results are null:

(anObject?.N$_f_foo()?.N$_f_bar()?.N$_f_baz())??null


Note: this would subtly change falsy messaging - messaging undefined would return null instead of undefined.