Making "super" work outside a literal?
seaneagan1 at gmail.com
Tue Jun 21 07:28:40 PDT 2011
On Sun, Jun 19, 2011 at 2:14 PM, Brendan Eich <brendan at mozilla.com> wrote:
> On Jun 19, 2011, at 10:20 AM, Axel Rauschmayer wrote:
> It would be nice if "super" could work in any method and not just those
> methods that are defined inside an object literal. Then, a method would have
> to know what object it resides in, e.g. via an implicit parameter.
> We wish to avoid another parameter computed potentially differently for each
> call. It will cost
What costs do you foresee? I am not sure that there is much to
compute. Assume a method call O.m(). Assume "m" is found on an
object P within O's protoype chain. This will result in P.m being
called, for which the "super binding" can simply be computed as
P.[[Prototype]]. Next assume a direct function call, e.g.
f.call(this) or f() (this === undefined), the "super binding" here
could just be calculated as this.[[Prototype]] or undefined if |this|
is not an object.
> , and it will lead to surprises.
What surprises do you foresee? I think a static |super| in light of
ES's dynamic |this| would actually be much more surprising. This
would lead to looking for properties in a static |super| object that
may be completely unrelated to the dynamic |this| value of a given
function activation, which would certainly be surprising.
> Also, anything reachable from |this| can be computed using ES5's Object.*
Wouldn't the ES5 Object.* APIs be unreliable and inconvenient for such
a calculation? It is impossible to determine which property name a
method m was accessed with from within m, and even if you assume a
static property name p, climbing the prototype chain of |this| to
determine on which object m was found via
|Object.getOwnPropertyDescriptor(prototypeChainObject, p)| may not be
accurate if there are any proxies in the prototype chain, or if
anything has changed in the prototype chain since it was initially
climbed by the engine.
> Quoting from
> http://wiki.ecmascript.org/doku.php?id=harmony:object_initialiser_super :
> When a function contains a reference to super, that function internally
> captures an internal reference to the [[Prototype]] of the object created by
> the enclosing object initialiser. If such a function is subsequently
> extracted from the original object and installed as a property value in some
> other object, the internal reference to the original [[Prototype]] is not
> modified. Essentially, when a function references super it is statically
> referencing a specific object that is identified when the function is
> defined and not the [[Prototype]] of the object from which the function was
> most recently retrieved.
> This behavior is consistent with that of most other languages that provide
> reflection function to extract methods containing super and then
> independently invoke them.
Consistency with other languages is valuable, but consistency with
this language (ES) is vital. A static |super| would be inconsistent
with ES's dynamic |this|. The semantics of |super| will be related to
the value of |this| no matter how |super| ends up being specified, and
thus the "super binding" should be calculated in terms of the "this
binding" if intra-language consistency is to be kept.
> es-discuss mailing list
> es-discuss at mozilla.org
More information about the es-discuss