Revenge of the double-curly [Was: return when desugaring to closures]
On 2008-10-10, at 02:29EDT, Brendan Eich wrote:
An agreement from TC39 this past sprint was that function definitions directly nested in blocks, not specified by ES3, defined block-local (let) bindings.
2008/10/10 P T Withington <ptw at pobox.com>:
Holy smokes. Does that mean we are all going to be writing
function ... () {{ ... }}
to get 'normal' scoping of function body declarations??? Will
var
meanlet
in those double-curly bodies? Might as well letlet
not be a keyword...
Haven't we been through this before? ES3 doesn't allow this, but all browsers do allow it. And all browsers have slightly or entirely different behaviour. The behaviour of Opera and IE on one hand and Mozilla and Safari on the other hand is entirely incompatible.
The Harmony decision is incompatible with all browsers, because the function wouldn't be usable before the block (breaks IE and Opera behaviour) and would fall out of scope when the block exits (breaks Mozilla and Safari behaviour).
For example, this works in Mozilla: if(true){ function fn(){return 'then-path';} }else{ function fn(){return 'else-path';} } fn(); // => 'then-path'
This would be broken by the Harmony design. On the other hand, the other browsers will result in 'else-path' in the current situation. (Is this a change in Safari? Unless I'm misremembering the results last time bundled Safari with Mozilla on this one.)
On Oct 10, 2008, at 5:44 AM, P T Withington wrote:
On 2008-10-10, at 02:29EDT, Brendan Eich wrote:
An agreement from TC39 this past spring was that function definitions directly nested in blocks, not specified by ES3, defined block-local (let) bindings.
Holy smokes. Does that mean we are all going to be writing
function ... () {{ ... }}
to get 'normal' scoping of function body declarations???
No. My words were unclear, sorry. I wrote "defined block-local (let)
bindings" meaning the functions defined in blocks bound their own
names only in the containing block, not in the variable object.
Will
var
meanlet
in those double-curly bodies?
No, var and let mean the same thing at top level.
P T Withington wrote:
On 2008-10-10, at 02:29EDT, Brendan Eich wrote:
An agreement from TC39 this past sprint was that function definitions directly nested in blocks, not specified by ES3, defined block-local (let) bindings.
Holy smokes. Does that mean we are all going to be writing
function ... () {{ ... }}
to get 'normal' scoping of function body declarations???
I don't think so, because at the top level of a function, a function-local declaration and a block-local declaration are the same thing. Have I missed something?
Will function definitions be in scope throughout the enclosing block, or only after and within the definition? E.g.
function f() { var x = "foo"; if (true) { print(x); // "function x() { x(); }", "undefined", "foo", // run-time exception, or static error?
x(); // call to x(), run-time exception, or static error?
function x() {
x(); // presumably allowed
}
} }
I think they should be in scope throughout the block -- for consistency with the "processed for function declarations" rule in ES3 section 13, because being able to put function declarations anywhere in a block may allow a clearer code layout in some cases, and to allow mutually recursive functions within a block.
On 2008-10-10, at 11:55EDT, Brendan Eich wrote:
On Oct 10, 2008, at 5:44 AM, P T Withington wrote:
On 2008-10-10, at 02:29EDT, Brendan Eich wrote:
An agreement from TC39 this past spring was that function
definitions directly nested in blocks, not specified by ES3, defined block-local (let) bindings.Holy smokes. Does that mean we are all going to be writing
function ... () {{ ... }}
to get 'normal' scoping of function body declarations???
No. My words were unclear, sorry. I wrote "defined block-local (let)
bindings" meaning the functions defined in blocks bound their own
names only in the containing block, not in the variable object.
Maybe I am trying to be too clever. Is it not the case (per cited
agreement) that:
function foo () {{ function bar () {...} }}
is sugar for:
function foo () { let bar = function () {...} }
whereas:
function foo () { function bar () {...} }
is sugar for:
function foo () { var bar = function () {...} }
? If so, perhaps you can see how I might imagine that:
function foo () {{ var bar = ...; }}
might be sugar for:
function foo () { let bar = ...; }
Just playing devil's advocate.
On Oct 10, 2008, at 11:58 AM, P T Withington wrote:
? If so, perhaps you can see how I might imagine that:
function foo () {{ var bar = ...; }}
might be sugar for:
function foo () { let bar = ...; }
Nope, not compatible and not what I meant.
Just the function's name is let-bound (block-scoped) for a function
defined directly in a block.
Brendan Eich wrote:
On Oct 10, 2008, at 11:58 AM, P T Withington wrote:
? If so, perhaps you can see how I might imagine that:
function foo () {{ var bar = ...; }}
might be sugar for:
function foo () { let bar = ...; }
Nope, not compatible and not what I meant.
It is correct to say, though, that:
function foo() { ... { var bar = baz; } ... }
is equivalent to
function foo() { let bar = undefined; ... { bar = baz; } ... }
That is, 'var' need not be primitive. Only 'let' needs to be primitive.
Similarly, if we are careful in specifying 'lambda' then 'function' need not be primitive, since it will be expressible as a rewrite to 'lambda'.
On Oct 11, 2008, at 7:25 AM, David-Sarah Hopwood wrote:
It is correct to say, though, that:
function foo() { ... { var bar = baz; } ... }
is equivalent to
function foo() { let bar = undefined; ... { bar = baz; } ... }
That is, 'var' need not be primitive. Only 'let' needs to be
primitive.
Indeed.
Similarly, if we are careful in specifying 'lambda' then 'function'
need not be primitive, since it will be expressible as a rewrite to
'lambda'.
Yes, this is called out already in
On 2008-10-10, at 02:29EDT, Brendan Eich wrote:
Holy smokes. Does that mean we are all going to be writing
function ... () {{ ... }}
to get 'normal' scoping of function body declarations??? Will
var
mean
let
in those double-curly bodies? Might as well letlet
notbe a keyword...
Dejá-vu, all over again.