From: webEater on
I am trying to implement a class pendant, that takes a data object as
argument and then changes that object instead of extending "this" with
all the data object's data (which means copying much data to a new
object). After some benchmarks I found out, that it's much faster not
to use the conventional new operator.

protoSupport = ({}).__proto__ === Object.prototype;

G = function (data) {

if (protoSupport) data.__proto__ = G.prototype;
else {

for (var k in G.prototype) {

data[k] = G.prototype[k];
}
}
data.z = 1;
return data;
};

G.prototype = {

k: function () {

return this.a;
},

l: function () {

return this.b;
},

constructor: G
};

So we do NOT use the new operator, instead we do:

obj = {a:1, b:2};
G(obj);

INTERESTINGLY, it's even faster, when protoSupport is false and we
iterate manually over all prototype properties. Does somebody know why?
From: Asen Bozhilov on
webEater wrote:
> I am trying to implement a class pendant, that takes a data object as
> argument and then changes that object instead of extending "this" with
> all the data object's data (which means copying much data to a new
> object). After some benchmarks I found out, that it's much faster not
> to use the conventional new operator.
>
> protoSupport = ({}).__proto__ === Object.prototype;

Undeclared assignment. And that test can be bogus. For example in
implementation which is not support `__proto__' anybody can do:

Object.prototype.__proto__ = Object.prototype;

And your test will lying. The better test is:

var PROTO_SUPPORT = !({__proto__ : null} instanceof Object);

>
> G = function (data) {

Undeclared assignment.

> So we do NOT use the new operator, instead we do:
>
> obj = {a:1, b:2};
> G(obj);

What is wrong on the follow code:

function G(a, b) {
this.a = a;
this.b = b;
this.z = 1;
}

G.prototype = {
constructor : G,
k : function () {
//...
},
l : function () {
//...
}
};

new G(1, 2);

Also that approach use smaller memory and is standard approach.

> INTERESTINGLY, it's even faster, when protoSupport is false and we
> iterate manually over all prototype properties. Does somebody know why?

Setter `__proto__` property should check for cycling chain. For
example:

var obj = {};
obj.__proto__ = obj;

During setting `__proto__' property you have reference to that object
via Scope chain and you can form cycling prototype chain, because of
that setter of `__proto__' should check for cycling chain and
performance of that is not very good.
Only object literals allow for optimization when you set `__proto__'
property because during evaluation of object literal you have not
reference to that object and therefore cannot be formed cycling chain.
For example:

var obj = {__proto__ : someObj};

So the last is safe and it allow for optimizations.

From: webEater on
On 15 Jun., 10:36, Asen Bozhilov <asen.bozhi...(a)gmail.com> wrote:
> webEater wrote:
> > I am trying to implement a class pendant, that takes a data object as
> > argument and then changes that object instead of extending "this" with
> > all the data object's data (which means copying much data to a new
> > object). After some benchmarks I found out, that it's much faster not
> > to use the conventional new operator.
>
> > protoSupport = ({}).__proto__ === Object.prototype;
>
> Undeclared assignment. And that test can be bogus. For example in
> implementation which is not support `__proto__' anybody can do:
>
> Object.prototype.__proto__ = Object.prototype;
>
> And your test will lying. The better test is:
>
> var PROTO_SUPPORT = !({__proto__ : null} instanceof Object);
>
>
>
> > G = function (data) {
>
> Undeclared assignment.
This is an example. For a CommonJS module it will be exports.G
>
> > So we do NOT use the new operator, instead we do:
>
> > obj = {a:1, b:2};
> > G(obj);
>
> What is wrong on the follow code:
>
> function G(a, b) {
>     this.a = a;
>     this.b = b;
>     this.z = 1;
>
> }
>

At first, nothing. But if a is big string, it is much faster not to
copy it to this.a - I have made some benchmarks which proof that.

> G.prototype = {
>     constructor : G,
>     k : function () {
>         //...
>     },
>     l : function () {
>         //...
>     }
>
> };
>
> new G(1, 2);
>
> Also that approach use smaller memory and is standard approach.
>
> > INTERESTINGLY, it's even faster, when protoSupport is false and we
> > iterate manually over all prototype properties. Does somebody know why?
>
> Setter `__proto__` property should check for cycling chain. For
> example:
>
> var obj = {};
> obj.__proto__ = obj;
>
> During setting `__proto__' property you have reference to that object
> via Scope chain and you can form cycling prototype chain, because of
> that setter of `__proto__' should check for cycling chain and
> performance of that is not very good.
> Only object literals allow for optimization when you set `__proto__'
> property because during evaluation of object literal you have not
> reference to that object and therefore cannot be formed cycling chain.
> For example:
>
> var obj = {__proto__ : someObj};
>
> So the last is safe and it allow for optimizations.

In the end I will use iteration over the prototype, because it's
faster an compatible with all browsers.
From: Thomas 'PointedEars' Lahn on
webEater wrote:

> Asen Bozhilov wrote:
>> What is wrong on the follow code:
>>
>> function G(a, b) {
>> this.a = a;
>> this.b = b;
>> this.z = 1;
>>
>> }
>
> At first, nothing. But if a is big string,

Which raises doubt as to whether that would be necessary in the first place
....

> it is much faster not to copy it to this.a - I have made some benchmarks
> which proof that.

Talk is cheap. Show me the code.
-- Linus Torvalds

> In the end I will use iteration over the prototype, because it's
> faster an compatible with all browsers.

Even faster is inheriting an object from another. You don't need the
__proto__ property for that.


PointedEars
--
Anyone who slaps a 'this page is best viewed with Browser X' label on
a Web page appears to be yearning for the bad old days, before the Web,
when you had very little chance of reading a document written on another
computer, another word processor, or another network. -- Tim Berners-Lee