Re: length property value for functions with parameter enhancements

2011-09-01 Thread Rick Waldron
Just want to clarify that neither jQuery nor its selector engine Sizzle have
any occurrences of function arity checking via the function length property.
Both codebases have occurrences of arguments.length checking

Rick




On Mon, Aug 29, 2011 at 9:20 PM, Allen Wirfs-Brock al...@wirfs-brock.comwrote:

 It looks like that in a number of these cases, what is being tested is the
 number of declared arguments  to the jquery Sizzle function which is a
 module function for its selector engine.  Very early versions of Sizzle seem
 to have had 3 formals (
 https://github.com/jquery/sizzle/commit/51ba623126501dd9381040bbdcbabe12cc9056db#diff-0
  )
 but it fairly soon evolved to take 4 formals (
 https://github.com/jquery/sizzle/blob/8b061ee512c50910d4e8e0247084446d03e90aa3/sizzle.js).
   I haven't found the code that does the actual test but this seems like
 the most likely reason to make such a test of that function.

 Presumably that sort of version testings is s plausible use case for a
 function's length although it isn't clear that it is any better than just
 putting a version tag property on such a function.

 Allen





 ___
 es-discuss mailing list
 es-discuss@mozilla.org
 https://mail.mozilla.org/listinfo/es-discuss


___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-09-01 Thread Dean Landolt
On Thu, Sep 1, 2011 at 11:38 AM, Rick Waldron waldron.r...@gmail.comwrote:

 Just want to clarify that neither jQuery nor its selector engine Sizzle
 have any occurrences of function arity checking via the function length
 property. Both codebases have occurrences of arguments.length checking


FTR this kind of arity checking is pretty common in the node.js world:
https://github.com/kriszyp/promised-io/blob/master/promise.js#L619
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-09-01 Thread Allen Wirfs-Brock

On Sep 1, 2011, at 8:55 AM, Dean Landolt wrote:

 
 
 On Thu, Sep 1, 2011 at 11:38 AM, Rick Waldron waldron.r...@gmail.com wrote:
 Just want to clarify that neither jQuery nor its selector engine Sizzle have 
 any occurrences of function arity checking via the function length property. 
 Both codebases have occurrences of arguments.length checking
 
 FTR this kind of arity checking is pretty common in the node.js world: 
 https://github.com/kriszyp/promised-io/blob/master/promise.js#L619
 


To clarify, it is indeed function arity checking that node.js is performing. In 
this case, it is assuming (maybe requiring is closer to fact) that all  
async functions take a callback as their last argument. and using that fact 
to generate wrapper functions that replace the callback function.

This pattern would break under the proposal we are discussing if somebody tried 
to define an async function with default value or rest parameters.  However, 
it would also break today if somebody tried to define an async function that 
solely used its arguments object to access arguments and neglected to declare 
any formal parameters.  Presumably in either case node.js should tell its users 
not to use such parameter patterns in defining async functions.

Regardless of whether or not we counted optional value parameters in 
determining the value of a function's length property this node.js pattern 
would be problematic if callers actually made use of the ability to optionally 
include/exclude default value arguments. So, it's not clear that  this use case 
helps us much in design our length value algorithm.

Allen



 ___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-31 Thread Tom Van Cutsem
2011/8/30 Brendan Eich bren...@mozilla.com

 On Aug 30, 2011, at 2:16 PM, David Bruant wrote:

 Actually that's what current function proxies do by default (no .prototype
 unless otherwise specified). My suggestion is to put a .prototype by default
 with keeping the option to opt-out (same with .length, etc.)

 Right, of course function proxies have to trap in order to emulate
 .prototype and other properties.


Indeed, that was our intent: fproxy.prototype and fproxy.length are
determined by the handler via the get trap.
This should work fine for fproxy.prototype (and it is actually consulted
when evaluating |obj instanceof fproxy|.)

For fproxy.length, the handler object can only return the call trap's length
if it has a reference to the call trap, which as David points out, in the
general case it does not. OTOH, typically a function proxy will wrap some
other target function f, in which case the handler would simply return
f.length, so I don't know whether this issue is such a big deal.

If one wraps an existing function f using the default ForwardingHandler like
so:
var fproxy = Proxy.createFunction(new ForwardingHandler(f), f);

Then fproxy.prototype, .length, .arguments, and .caller will all work as
expected. So the default ForwardingHandler is in a sense already the
convenient library that Andreas alluded to.

I do notice that .prototype and .length are non-configurable properties, so
that ups the ante for proxies being able to emulate non-configurable
properties (more about that later).

Cheers,
Tom
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-31 Thread David Bruant

Le 31/08/2011 13:24, Tom Van Cutsem a écrit :

2011/8/30 Brendan Eich bren...@mozilla.com mailto:bren...@mozilla.com

On Aug 30, 2011, at 2:16 PM, David Bruant wrote:

Actually that's what current function proxies do by default (no
.prototype unless otherwise specified). My suggestion is to put a
.prototype by default with keeping the option to opt-out (same
with .length, etc.)

Right, of course function proxies have to trap in order to emulate
.prototype and other properties.


Indeed, that was our intent: fproxy.prototype and fproxy.length are 
determined by the handler via the get trap.
This should work fine for fproxy.prototype (and it is actually 
consulted when evaluating |obj instanceof fproxy|.)


For fproxy.length, the handler object can only return the call trap's 
length if it has a reference to the call trap, which as David points 
out, in the general case it does not. OTOH, typically a function proxy 
will wrap some other target function f, in which case the handler 
would simply return f.length, so I don't know whether this issue is 
such a big deal.
True. Still, a handler needs an access to the callTrap in order to 
retrieve its length in the general case. And with the current API, it 
may be impossible for an already created handler (not one created 
through a factory) to access to the callTrap, making impossible to 
access its .length and .prototype
I agree that the typical case is to wrap, but is it a sufficient reason 
for people not wrapping to not be able to properly emulate function.length?


If one wraps an existing function f using the default 
ForwardingHandler like so:

var fproxy = Proxy.createFunction(new ForwardingHandler(f), f);
Alternatively, i suggested earlier this summer [1] to put callTrap and 
constructTrap as part of the handler. This which would solve the problem 
of a handler having access to the callTrap (this.call from any other 
trap) and would also solve the question what if handler.call.length !== 
handler.construct.length? which would be left to the author discretion.


David

[1] https://mail.mozilla.org/pipermail/es-discuss/2011-August/016247.html
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-31 Thread Tom Van Cutsem
I coded up a hypothetical Proxy.createConstructor function that creates a
function proxy initialized according to ES5.1 section 13.2: 
https://gist.github.com/1183514

Given the ease with which this can be expressed, I'm not sure it merits
dedicated support, unless I overlooked something.

Cheers,
Tom

2011/8/31 Tom Van Cutsem tomvc...@gmail.com

 2011/8/30 Brendan Eich bren...@mozilla.com

 On Aug 30, 2011, at 2:16 PM, David Bruant wrote:

 Actually that's what current function proxies do by default (no .prototype
 unless otherwise specified). My suggestion is to put a .prototype by default
 with keeping the option to opt-out (same with .length, etc.)

 Right, of course function proxies have to trap in order to emulate
 .prototype and other properties.


 Indeed, that was our intent: fproxy.prototype and fproxy.length are
 determined by the handler via the get trap.
 This should work fine for fproxy.prototype (and it is actually consulted
 when evaluating |obj instanceof fproxy|.)

 For fproxy.length, the handler object can only return the call trap's
 length if it has a reference to the call trap, which as David points out, in
 the general case it does not. OTOH, typically a function proxy will wrap
 some other target function f, in which case the handler would simply return
 f.length, so I don't know whether this issue is such a big deal.

 If one wraps an existing function f using the default ForwardingHandler
 like so:
 var fproxy = Proxy.createFunction(new ForwardingHandler(f), f);

 Then fproxy.prototype, .length, .arguments, and .caller will all work as
 expected. So the default ForwardingHandler is in a sense already the
 convenient library that Andreas alluded to.

 I do notice that .prototype and .length are non-configurable properties, so
 that ups the ante for proxies being able to emulate non-configurable
 properties (more about that later).

 Cheers,
 Tom

___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-31 Thread Andreas Rossberg
On 31 August 2011 15:21, Tom Van Cutsem tomvc...@gmail.com wrote:

 I coded up a hypothetical Proxy.createConstructor function that creates a
 function proxy initialized according to ES5.1 section 13.2: 
 https://gist.github.com/1183514


Nit: invoking callTrap.call assumes that callTrap has an actual call method.
But you want to work this for call traps that are themselves proxies and
don't necessarily have that (or don't we?). So you need to do

  Function.prototype.apply.call(callTrap, instance, arguments)

(assuming nobody messed with that either, of course).

This turns up quite frequently, in fact. With proxies, it is really
error-prone that all these functions have been made available as methods on
{Object,Function}.prototype, instead of being separate. Morally, these
methods used to be part of the implicit contracts of object and function
types that everybody relies on. But proxies break those contracts! At least
for functions, this is really a problem IMO (for plain objects, the contract
was already invalidated by allowing Object.create(null)).

/Andreas
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-30 Thread Tom Van Cutsem
2011/8/29 Allen Wirfs-Brock al...@wirfs-brock.com

 I think 15.3.4.5 should be generalize so that the computation of the length
 property isn't predicted by [[Class]]=='Function' but instead should just
 use the the numeric value of the target's length property, if it exists.  If
 the target does not have a length property or if its value is not a number
 then the bound function would get a length value of 0.


That seems reasonable. I guess it implies that callable host objects that
hitherto had a length of 0 might now have a different length, but for
function proxies it seems like the right thing to do.

Cheers,
Tom
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-30 Thread David Bruant
Le 29/08/2011 16:43, Tom Van Cutsem a écrit :
 (changed subject to fork off discussion on function proxies)

 2011/8/29 Allen Wirfs-Brock al...@wirfs-brock.com
 mailto:al...@wirfs-brock.com

 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
   True, and actually, there are more issues with length  function
  proxies. I don't have my notes with me right now, but for
 example, it
  is not clear at all what length Function.prototype.bind should set
  when called on a function proxy. 0? 1? Should it try to get the
 length
  property from the proxy and subtract N? What if length is not
 defined
  on the proxy, or not a (natural) number?

 The ES5.1 spec.  defines how how bind determines the length for
 the function it creates based upon the length property of the
 target function.  I would expect the same rules would apply when
 the target is a function proxy.


 I see two options here:
 a) either query the function proxy for its length property via its
 get trap, and convert the result using ToInteger, introducing a new
 error case if the conversion fails.
 b) or determine length based on the function proxy's call trap
 (which is presumably a non-proxy function. If it is a function proxy
 itself, recurse)

 The spec currently uses the wording: Let L be the length property of
 Target ... (ES5.1 section 15.3.4.5)
 If that is not equivalent to Let L be the result of calling the
 [[Get]] internal method of Target with argument length, then option
 b) seems better.
There is no mention of function proxy lengths in
harmony:proxies_semantics [1] nor in harmony:proxies and i'd like to
discuss this.
-
var f = Proxy.createFunction(functionHandler, function(){}, function(){})
var l = f.length; // ?
-
Currently, nothing is really said about how is handled f.length,
f.prototype and such. So, it seems to be left to the proxy author.
In order to facilitate the author work, it could be possible to have an
ES5.1-13.2-like function proxy constructor especially when it comes to
steps 15, 17, 18 (i'm in doubt with steps 5 and 19).
Step 15 would be a way for the engine to communicate with the handler to
pass the [[Call]].length value. In order to initially set the length
value, i think it would make sense to take [[Call]].length too (what if
[[Call]].length !== [[Construct]].length?). Also, it would facilitate
the way the handler has access to [[Call]].length when writing
functionHandler.get and functionHandler.get{Own}PropertyDescriptor
It could be left to the programmer the initiative to refuse the addition
of the length property (if it's necessary to emulate an host object) (by
returning false at the end of the defineProperty trap iirc)

This would facilitate the author work when it comes to creating
functions that look like functions without having to always include some
initialization code for .length, .prototype and such.
It will still be possible to opt-out of .length or .prototype if the
author doesn't

David

[1] http://wiki.ecmascript.org/doku.php?id=harmony:proxies_semantics
[2] http://wiki.ecmascript.org/doku.php?id=strawman:fixed_properties
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-30 Thread Andreas Rossberg
On 30 August 2011 18:41, David Bruant david.bru...@labri.fr wrote:

 This would facilitate the author work when it comes to creating functions
 that look like functions without having to always include some
 initialization code for .length, .prototype and such.
 It will still be possible to opt-out of .length or .prototype if the author
 doesn't


I don't think it's worth introducing special cases in the semantics,
especially not for something like length. Proxy authors already have to do a
lot of similar work, e.g. to make all the standard Object.prototype and
Function.prototype methods available on proxies.

I think this problem is something that should be solved by the library, not
the proxy API itself. Maybe we can find some nice building blocks for
handlers that make available the basic functionality in a convenient and
extensible way?

Another interesting case btw (although outside the standard proper) is
__proto__...

/Andreas
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-30 Thread David Bruant
Le 30/08/2011 21:40, Brendan Eich a écrit :
 On Aug 30, 2011, at 11:00 AM, Andreas Rossberg wrote:

 On 30 August 2011 18:41, David Bruant david.bru...@labri.fr
 mailto:david.bru...@labri.fr wrote:

 This would facilitate the author work when it comes to creating
 functions that look like functions without having to always
 include some initialization code for .length, .prototype and such.
 It will still be possible to opt-out of .length or .prototype if
 the author doesn't


 I don't think it's worth introducing special cases in the semantics,
 especially not for something like length.

 Perhaps, but I think David has a stronger case for opting out of
 .prototype.
Actually that's what current function proxies do by default (no
.prototype unless otherwise specified). My suggestion is to put a
.prototype by default with keeping the option to opt-out (same with
.length, etc.)

 Indeed self-hosting some of the ES1-5 builtins requires doing so, somehow.
Couldn't it be achived with bound functions (which do not have an own
prototype property)?

David
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-30 Thread Brendan Eich
On Aug 30, 2011, at 2:16 PM, David Bruant wrote:

 Le 30/08/2011 21:40, Brendan Eich a écrit :
 
 On Aug 30, 2011, at 11:00 AM, Andreas Rossberg wrote:
 
 On 30 August 2011 18:41, David Bruant david.bru...@labri.fr wrote:
 This would facilitate the author work when it comes to creating functions 
 that look like functions without having to always include some 
 initialization code for .length, .prototype and such. 
 It will still be possible to opt-out of .length or .prototype if the author 
 doesn't
 
 I don't think it's worth introducing special cases in the semantics, 
 especially not for something like length.
 
 Perhaps, but I think David has a stronger case for opting out of .prototype.
 Actually that's what current function proxies do by default (no .prototype 
 unless otherwise specified). My suggestion is to put a .prototype by default 
 with keeping the option to opt-out (same with .length, etc.)

Right, of course function proxies have to trap in order to emulate .prototype 
and other properties.


 Indeed self-hosting some of the ES1-5 builtins requires doing so, somehow.
 Couldn't it be achived with bound functions (which do not have an own 
 prototype property)?

Built-ins do not bind |this|, though -- many are generic (IIRC these are the 
ones V8 self-hosts).

Also, binding costs memory and cycles, it hurts a bit when creating these 
things. This can add up.

/be___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Andreas Rossberg
On 29 August 2011 01:36, Allen Wirfs-Brock al...@wirfs-brock.com wrote:
 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
 True, and actually, there are more issues with length  function
 proxies. I don't have my notes with me right now, but for example, it
 is not clear at all what length Function.prototype.bind should set
 when called on a function proxy. 0? 1? Should it try to get the length
 property from the proxy and subtract N? What if length is not defined
 on the proxy, or not a (natural) number?

 The ES5.1 spec.  defines how how bind determines the length for the function 
 it creates based upon the length property of the target function.  I would 
 expect the same rules would apply when the target is a function proxy.

Ah, right, I was looking at the 5.0 spec 8-}. However, that is still
not good enough for function proxies, because you have no guarantee
that they define length at all, or make it a natural number. So we at
least have to include additional error cases, and a solution for them.

     function bam(a,b,c=0,...d) {} //bam.length==2   BTW, is this legal?

 Makes sense. (And yes, I don't see why the latter shouldn't be legal.)
 Because the is a  potential for misinterpreting the user intent on such a 
 call.  For
    bam('a','b',1,2,3)
 we surely have to interpret the argument/parameter mapping as:
     a='a',b='b',c=1,d=[2,3]
 but it is easy to imagine a programmer intending
     a='a',b='b',c=0,d=[1,2,3]
 Making it illegal to have a formal parameter list that has both optional and 
 result parameters might result the likelihood of that confusion,

Hm, that doesn't sound like a very JavaScripty argument :). If you buy
into optional arguments at all, then I can certainly envision valid
use cases for combining them with rest arguments.

 If there are no non-optional or non-rest formal parameters the length is 1.
     function bar1(a=0) {} //bar1.length=1
     function baz1(a=0,b=1,c=2) {} //baz1.length=1
     function bam1(...a) {} //bam1.length==1

 I'm not so sure about this, it seems incoherent. Why not 0, especially
 for the first two? You mentioned builtins like Array above, but I
 would rather count them as the exception to the rule (especially given
 that the builtins don't seem entirely consistent wrt length anyway).

 In my proposal, I am decided to make a clear distinction between truly empty  
 formal parameter lists and  those with only various forms of optional formal 
 parameters by only giving a 0 length to the empty formals case.  That's a 
 debatable decision but it seems desirable to distinguish the two cases and 
 the built-ins is the only precedent that we have to follow.

I guess I don't see what is special about empty argument lists. Why
would you want to make a clearer distinction between the argument
lists () and (a=0), than between (x) and (x, a=0)? You seem to be
introducing a discontinuity.

 FWIW, one could also argue for setting length to +infinity for
 functions with only rest parameters. :)

 But there is no precedent for that and surely infinity is not the typical 
 number of arguments.

Yeah, I wasn't being serious.

 I'm not sure if there is any real use case for the length property of 
 ECMAScript functions.  Does anybody know of one? Regardless, I do think we 
 can get rid of it.

Do not, I suppose? (Unfortunately, as I was wondering the same.)

/Andreas
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-29 Thread Tom Van Cutsem
(changed subject to fork off discussion on function proxies)

2011/8/29 Allen Wirfs-Brock al...@wirfs-brock.com

 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
   True, and actually, there are more issues with length  function
  proxies. I don't have my notes with me right now, but for example, it
  is not clear at all what length Function.prototype.bind should set
  when called on a function proxy. 0? 1? Should it try to get the length
  property from the proxy and subtract N? What if length is not defined
  on the proxy, or not a (natural) number?

 The ES5.1 spec.  defines how how bind determines the length for the
 function it creates based upon the length property of the target function.
  I would expect the same rules would apply when the target is a function
 proxy.


I see two options here:
a) either query the function proxy for its length property via its get
trap, and convert the result using ToInteger, introducing a new error case
if the conversion fails.
b) or determine length based on the function proxy's call trap (which is
presumably a non-proxy function. If it is a function proxy itself, recurse)

The spec currently uses the wording: Let L be the length property of Target
... (ES5.1 section 15.3.4.5)
If that is not equivalent to Let L be the result of calling the [[Get]]
internal method of Target with argument length, then option b) seems
better.

There is precedent for using the call trap as a substitute for the function
proxy: Function.prototype.toString.call(aFunctionProxy)  will also use the
call trap's toString representation rather than trapping the handler.

Cheers,
Tom
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-29 Thread Mark S. Miller
On Mon, Aug 29, 2011 at 7:43 AM, Tom Van Cutsem tomvc...@gmail.com wrote:

 (changed subject to fork off discussion on function proxies)

 2011/8/29 Allen Wirfs-Brock al...@wirfs-brock.com

 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
   True, and actually, there are more issues with length  function
  proxies. I don't have my notes with me right now, but for example, it
  is not clear at all what length Function.prototype.bind should set
  when called on a function proxy. 0? 1? Should it try to get the length
  property from the proxy and subtract N? What if length is not defined
  on the proxy, or not a (natural) number?

 The ES5.1 spec.  defines how how bind determines the length for the
 function it creates based upon the length property of the target function.
  I would expect the same rules would apply when the target is a function
 proxy.


 I see two options here:
 a) either query the function proxy for its length property via its get
 trap, and convert the result using ToInteger, introducing a new error case
 if the conversion fails.
 b) or determine length based on the function proxy's call trap (which is
 presumably a non-proxy function. If it is a function proxy itself, recurse)

 The spec currently uses the wording: Let L be the length property of
 Target ... (ES5.1 section 15.3.4.5)
 If that is not equivalent to Let L be the result of calling the [[Get]]
 internal method of Target with argument length, then option b) seems
 better.

 There is precedent for using the call trap as a substitute for the function
 proxy: Function.prototype.toString.call(aFunctionProxy)  will also use the
 call trap's toString representation rather than trapping the handler.


I don't have any strong preference regarding #a vs #b. However, I don't
think Function.prototype.toString.call(aFunctionProxy) is a relevant
precedent. For .length, we have the choice of #a or #b. For
...toString.call, what other option could there be besides the choice we
made?

-- 
Cheers,
--MarkM
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: Function proxy length (Was: length property value for functions with parameter enhancements)

2011-08-29 Thread Allen Wirfs-Brock

On Aug 29, 2011, at 7:43 AM, Tom Van Cutsem wrote:

 (changed subject to fork off discussion on function proxies)
 
 2011/8/29 Allen Wirfs-Brock al...@wirfs-brock.com
 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
   True, and actually, there are more issues with length  function
  proxies. I don't have my notes with me right now, but for example, it
  is not clear at all what length Function.prototype.bind should set
  when called on a function proxy. 0? 1? Should it try to get the length
  property from the proxy and subtract N? What if length is not defined
  on the proxy, or not a (natural) number?
 
 The ES5.1 spec.  defines how how bind determines the length for the function 
 it creates based upon the length property of the target function.  I would 
 expect the same rules would apply when the target is a function proxy.
 
 I see two options here:
 a) either query the function proxy for its length property via its get 
 trap, and convert the result using ToInteger, introducing a new error case if 
 the conversion fails.
 b) or determine length based on the function proxy's call trap (which is 
 presumably a non-proxy function. If it is a function proxy itself, recurse)
 
 The spec currently uses the wording: Let L be the length property of Target 
 ... (ES5.1 section 15.3.4.5)
 If that is not equivalent to Let L be the result of calling the [[Get]] 
 internal method of Target with argument length, then option b) seems 
 better.

It should be considered to be a [[Get]] (and should be restarted as such).

A deeper question is whether or not function proxy objects are ES5 
[[Class]]=='Function' objects (regardless of how this is actually expressed in 
the ES6 spec.)  For ES5, the distinction between objects that are callable and 
more specific objects where [[Class]]=='Function' was that 
[[Class]]=='Function' implies all of the invariants from sections 13.2 and 15.3 
and their subsections while isCallable only means that the object supports 
[[Call]]. For example, such object always have a immutable 'length' property 
whose value is a number but host objects that are callable might not have such 
a property.  Hence the test in 15.3.4.5 step 15.

Because of their nature, it would seem unreasonable to assume that function 
proxy objects conform to all of the 13.2 and 15.3 invariants. 

That means that according to 15.3.4.5 a bound function that targets a function 
proxy would have a length of 0.  That doesn't seem quite right either.  I think 
15.3.4.5 should be generalize so that the computation of the length property 
isn't predicted by [[Class]]=='Function' but instead should just use the the 
numeric value of the target's length property, if it exists.  If the target 
does not have a length property or if its value is not a number then the bound 
function would get a length value of 0.


Allen

___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Allen Wirfs-Brock

On Aug 29, 2011, at 2:32 AM, Andreas Rossberg wrote:

 On 29 August 2011 01:36, Allen Wirfs-Brock al...@wirfs-brock.com wrote:
 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
 True, and actually, there are more issues with length  function
 proxies. I don't have my notes with me right now, but for example, it
 is not clear at all what length Function.prototype.bind should set
 when called on a function proxy. 0? 1? Should it try to get the length
 property from the proxy and subtract N? What if length is not defined
 on the proxy, or not a (natural) number?
 
 The ES5.1 spec.  defines how how bind determines the length for the function 
 it creates based upon the length property of the target function.  I would 
 expect the same rules would apply when the target is a function proxy.
 
 Ah, right, I was looking at the 5.0 spec 8-}. However, that is still
 not good enough for function proxies, because you have no guarantee
 that they define length at all, or make it a natural number. So we at
 least have to include additional error cases, and a solution for them.

those cases probably fall under step 16 of 15.3.4.5 but we'll have to be more 
explicit about that.

 
 function bam(a,b,c=0,...d) {} //bam.length==2   BTW, is this legal?
 
 Makes sense. (And yes, I don't see why the latter shouldn't be legal.)
 Because the is a  potential for misinterpreting the user intent on such a 
 call.  For
bam('a','b',1,2,3)
 we surely have to interpret the argument/parameter mapping as:
 a='a',b='b',c=1,d=[2,3]
 but it is easy to imagine a programmer intending
 a='a',b='b',c=0,d=[1,2,3]
 Making it illegal to have a formal parameter list that has both optional and 
 result parameters might result the likelihood of that confusion,
 
 Hm, that doesn't sound like a very JavaScripty argument :). If you buy
 into optional arguments at all, then I can certainly envision valid
 use cases for combining them with rest arguments.

Which is the source of the potential confusion because all of the optional 
parameters get populated with values before the rest argument gets any values.  

...
 
 In my proposal, I am decided to make a clear distinction between truly empty 
  formal parameter lists and  those with only various forms of optional 
 formal parameters by only giving a 0 length to the empty formals case.  
 That's a debatable decision but it seems desirable to distinguish the two 
 cases and the built-ins is the only precedent that we have to follow.
 
 I guess I don't see what is special about empty argument lists. Why
 would you want to make a clearer distinction between the argument
 lists () and (a=0), than between (x) and (x, a=0)? You seem to be
 introducing a discontinuity.

Given, that I have yet to think of a reasonable use case for function length 
properties, all of these rationalizations a pretty conceptual.

However, () seems like a clear statement that no arguments are required or 
expected while (a=0) says that an argument does have some meaning.  This seems 
like a worthwhile distinction to make even though 1 may not be the typical 
number of arguments.

Allen


___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Brendan Eich
On Aug 28, 2011, at 4:36 PM, Allen Wirfs-Brock wrote:

 On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:
 
 On 27 August 2011 00:34, Allen Wirfs-Brock al...@wirfs-brock.com wrote:
 If the formal parameter list includes any non-optional, non-rest formal
 parameters, the length is the total number of non-optional/non-rest formal
 parameters.
 For example:
function bar(a,b,c) {} //bar.length=3
function baz(a,b,c=0) {} //baz.length=2
function bam(a,b,c=0,...d) {} //bam.length==2   BTW, is this legal?
 
 Makes sense. (And yes, I don't see why the latter shouldn't be legal.)
 Because the is a  potential for misinterpreting the user intent on such a 
 call.  For
bam('a','b',1,2,3) 
 we surely have to interpret the argument/parameter mapping as:
 a='a',b='b',c=1,d=[2,3] 
 but it is easy to imagine a programmer intending
 a='a',b='b',c=0,d=[1,2,3] 
 Making it illegal to have a formal parameter list that has both optional and 
 result parameters might result the likelihood of that confusion,  

That's too restrictive. There are lots of ways to go wrong in JS, we don't try 
to put programmers in a five-point harness.

Python:

 def foo(a,b,c=1,*d):
...   print(a, b, c, d)
... 
 foo(0,1,2,3,4)
0 1 2 (3, 4)
 foo(0,1,2,3)
0 1 2 (3,)
 foo(0,1,2)
0 1 2 ()
 foo(0,1)
0 1 1 ()

(Python reflects rest params [splats] as tuples not lists.)

Ruby is of course pretty similar:

def foo(a,b,c=1,*d)
  print a, b, c, d, \n
end
foo(0,1,2,3,4)
foo(0,1,2,3)
foo(0,1,2)
foo(0,1)
^D
01234
0123
012
011

(My Ruby REPL skills are sad -- ugly run-together stdout follows the TTY EOF ^D 
above.)


 If there are no non-optional or non-rest formal parameters the length is 1.
function bar1(a=0) {} //bar1.length=1
function baz1(a=0,b=1,c=2) {} //baz1.length=1
function bam1(...a) {} //bam1.length==1
 
 I'm not so sure about this, it seems incoherent. Why not 0, especially
 for the first two? You mentioned builtins like Array above, but I
 would rather count them as the exception to the rule (especially given
 that the builtins don't seem entirely consistent wrt length anyway).
 
 In my proposal, I am decided to make a clear distinction between truly empty  
 formal parameter lists and  those with only various forms of optional formal 
 parameters by only giving a 0 length to the empty formals case.  That's a 
 debatable decision but it seems desirable to distinguish the two cases and 
 the built-ins is the only precedent that we have to follow.

You make a distinction but create an ambiguity between

function foo(a=0)... // length 1
function bar(a=0,b=1) // length 1

That seems no more consistent (and less coherent as Andreas put it). If 
trailing optional parameters do not contribute to length, then we have a 
consistent single rule for length. That it does not match all built-ins is sad 
history, not to be rewritten lightly but not to overdetermine the future.


 I'm not sure if there is any real use case for the length property of 
 ECMAScript functions.  Does anybody know of one? Regardless, I do think we 
 can get rid of it.

Working on instrumentation to find uses on the web. More in a bit,

/be
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Brendan Eich
On Aug 29, 2011, at 11:29 AM, Allen Wirfs-Brock wrote:

 Hm, that doesn't sound like a very JavaScripty argument :). If you buy
 into optional arguments at all, then I can certainly envision valid
 use cases for combining them with rest arguments.
 
 Which is the source of the potential confusion because all of the optional 
 parameters get populated with values before the rest argument gets any 
 values.  

There's no confusion, IMHO. The order is left to right -- this matters for 
parameter default values in and of themselves. The precedent in nearby 
languages is strong. I am pretty opposed to making this an error case. It 
cannot of course be a case where right-to-left evaluation happens in any form 
(rest parameter eats actuals, leaving none in the middle for default 
parameters).


 I guess I don't see what is special about empty argument lists. Why
 would you want to make a clearer distinction between the argument
 lists () and (a=0), than between (x) and (x, a=0)? You seem to be
 introducing a discontinuity.
 
 Given, that I have yet to think of a reasonable use case for function length 
 properties, all of these rationalizations a pretty conceptual.
 
 However, () seems like a clear statement that no arguments are required or 
 expected while (a=0) says that an argument does have some meaning.  This 
 seems like a worthwhile distinction to make even though 1 may not be the 
 typical number of arguments.

You can't use one integer-valued property to convey two meanings. F.length is 
either minimum non-default/rest parameters, or a count of non-rest parameters. 
I don't see a sane alternative. The count of non-rest parameters is not that 
interesting, since it is one fewer than the full count of all parameters 
(modulo destructuring, where it must count each actual position, not all the 
names of destructured-to formals). That leaves F.length counting only 
non-default/rest params.

/be
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Allen Wirfs-Brock

On Aug 29, 2011, at 1:36 PM, Brendan Eich wrote:

 
 You can't use one integer-valued property to convey two meanings. F.length is 
 either minimum non-default/rest parameters, or a count of non-rest 
 parameters. I don't see a sane alternative. The count of non-rest parameters 
 is not that interesting, since it is one fewer than the full count of all 
 parameters (modulo destructuring, where it must count each actual position, 
 not all the names of destructured-to formals). That leaves F.length counting 
 only non-default/rest params.
 

I can think of two more plausible ones:

1) the number of parameter positions specified in the formal parameter list 
include  (I'm avoiding talking about names because of destructing):
  function (a,b=1,...c) {}  //length==3
  function (...c) {} // length=1

2) the number of parameter positions (including the rest parameter if 
specified) that precede the first default-value parameter (or the end of the 
list if there are no default-value parameters):
  function (a,b,c) {}  //length==3
  function (a,b,...c) {}  //length==3  
  function (...c) {} // length=1
  function (a=1,b=2) {}  //length==0
 function (a,b=1) {}  //length==1
 function (a,b=1,...c) {}  //length==1

1) is the simplest rule and in the absence of a clear use case is probably as 
good as any other

2) Treats rest as meaning usually at least one (unless following a 
default-value parameter) which seems to be the way open-ended parameter lists 
were interpreted in assigning length to most such Chapter 15 functions.  I 
think that this rule would yield the most matches  with the specified lengths 
of chapter 15 functions when their signatures are rewritten using default-value 
and rest parameter notation.

Allen

___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Brendan Eich
Here's a log with complete decompilation including the function whose .length 
was accessed.

file:line length function

/be



funlen.log
Description: Binary data



___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-29 Thread Allen Wirfs-Brock
It looks like that in a number of these cases, what is being tested is the 
number of declared arguments  to the jquery Sizzle function which is a module 
function for its selector engine.  Very early versions of Sizzle seem to have 
had 3 formals 
(https://github.com/jquery/sizzle/commit/51ba623126501dd9381040bbdcbabe12cc9056db#diff-0
 ) but it fairly soon evolved to take 4 formals 
(https://github.com/jquery/sizzle/blob/8b061ee512c50910d4e8e0247084446d03e90aa3/sizzle.js
 ).  I haven't found the code that does the actual test but this seems like the 
most likely reason to make such a test of that function.

Presumably that sort of version testings is s plausible use case for a 
function's length although it isn't clear that it is any better than just 
putting a version tag property on such a function.

Allen




___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-28 Thread Allen Wirfs-Brock

On Aug 27, 2011, at 6:12 AM, Andreas Rossberg wrote:

 On 27 August 2011 00:34, Allen Wirfs-Brock al...@wirfs-brock.com wrote:
 Something we need to define for ES.next is how to compute the length
 property value for functions whose formal parameter list includes optional
 and/or rest parameters.
 
 True, and actually, there are more issues with length  function
 proxies. I don't have my notes with me right now, but for example, it
 is not clear at all what length Function.prototype.bind should set
 when called on a function proxy. 0? 1? Should it try to get the length
 property from the proxy and subtract N? What if length is not defined
 on the proxy, or not a (natural) number?

The ES5.1 spec.  defines how how bind determines the length for the function it 
creates based upon the length property of the target function.  I would expect 
the same rules would apply when the target is a function proxy.

 
 This is probably something the proxy proposal has to resolve
 eventually, but it's worth keeping in mind for the broader picture.
 
 So, what is a length determination algorithm that recognizes optional/rest
 arguments and is consistent with the stated intent of length and (as much as
 possible)existing section 15 definitions.  Here is one proposal:
 The length is 0 only if the formal parameter list is empty.
 For example:
function foo() {};  //foo.length==1
 
 You meant ==0 here, right?
right
 
 If the formal parameter list includes any non-optional, non-rest formal
 parameters, the length is the total number of non-optional/non-rest formal
 parameters.
 For example:
 function bar(a,b,c) {} //bar.length=3
 function baz(a,b,c=0) {} //baz.length=2
 function bam(a,b,c=0,...d) {} //bam.length==2   BTW, is this legal?
 
 Makes sense. (And yes, I don't see why the latter shouldn't be legal.)
Because the is a  potential for misinterpreting the user intent on such a call. 
 For
bam('a','b',1,2,3) 
we surely have to interpret the argument/parameter mapping as:
 a='a',b='b',c=1,d=[2,3] 
but it is easy to imagine a programmer intending
 a='a',b='b',c=0,d=[1,2,3] 
Making it illegal to have a formal parameter list that has both optional and 
result parameters might result the likelihood of that confusion,  

 
 If there are no non-optional or non-rest formal parameters the length is 1.
 function bar1(a=0) {} //bar1.length=1
 function baz1(a=0,b=1,c=2) {} //baz1.length=1
 function bam1(...a) {} //bam1.length==1
 
 I'm not so sure about this, it seems incoherent. Why not 0, especially
 for the first two? You mentioned builtins like Array above, but I
 would rather count them as the exception to the rule (especially given
 that the builtins don't seem entirely consistent wrt length anyway).

In my proposal, I am decided to make a clear distinction between truly empty  
formal parameter lists and  those with only various forms of optional formal 
parameters by only giving a 0 length to the empty formals case.  That's a 
debatable decision but it seems desirable to distinguish the two cases and the 
built-ins is the only precedent that we have to follow.


 
 FWIW, one could also argue for setting length to +infinity for
 functions with only rest parameters. :)

But there is no precedent for that and surely infinity is not the typical 
number of arguments.

I'm not sure if there is any real use case for the length property of 
ECMAScript functions.  Does anybody know of one? Regardless, I do think we can 
get rid of it.

Allen


___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss


Re: length property value for functions with parameter enhancements

2011-08-27 Thread Andreas Rossberg
On 27 August 2011 00:34, Allen Wirfs-Brock al...@wirfs-brock.com wrote:
 Something we need to define for ES.next is how to compute the length
 property value for functions whose formal parameter list includes optional
 and/or rest parameters.

True, and actually, there are more issues with length  function
proxies. I don't have my notes with me right now, but for example, it
is not clear at all what length Function.prototype.bind should set
when called on a function proxy. 0? 1? Should it try to get the length
property from the proxy and subtract N? What if length is not defined
on the proxy, or not a (natural) number?

This is probably something the proxy proposal has to resolve
eventually, but it's worth keeping in mind for the broader picture.

 So, what is a length determination algorithm that recognizes optional/rest
 arguments and is consistent with the stated intent of length and (as much as
 possible)existing section 15 definitions.  Here is one proposal:
 The length is 0 only if the formal parameter list is empty.
 For example:
    function foo() {};  //foo.length==1

You meant ==0 here, right?

 If the formal parameter list includes any non-optional, non-rest formal
 parameters, the length is the total number of non-optional/non-rest formal
 parameters.
 For example:
     function bar(a,b,c) {} //bar.length=3
     function baz(a,b,c=0) {} //baz.length=2
     function bam(a,b,c=0,...d) {} //bam.length==2   BTW, is this legal?

Makes sense. (And yes, I don't see why the latter shouldn't be legal.)

 If there are no non-optional or non-rest formal parameters the length is 1.
     function bar1(a=0) {} //bar1.length=1
     function baz1(a=0,b=1,c=2) {} //baz1.length=1
     function bam1(...a) {} //bam1.length==1

I'm not so sure about this, it seems incoherent. Why not 0, especially
for the first two? You mentioned builtins like Array above, but I
would rather count them as the exception to the rule (especially given
that the builtins don't seem entirely consistent wrt length anyway).

FWIW, one could also argue for setting length to +infinity for
functions with only rest parameters. :)

/Andreas
___
es-discuss mailing list
es-discuss@mozilla.org
https://mail.mozilla.org/listinfo/es-discuss