bem-sdk-archive / bem-entity-name

BEM entity name representation. DEPRECATED →
https://github.com/bem/bem-sdk/tree/master/packages/entity-name
Other
5 stars 3 forks source link

Getters are slow, can we change it? #3

Closed qfox closed 8 years ago

qfox commented 8 years ago

Why we decide to use getters?

blond commented 8 years ago

Getters are slow

Any proofs?

Why we decide to use getters?

  1. These fields can not be overwritten
  2. id and type fields can be calculated only when necessary
qfox commented 8 years ago

http://jsperf.com/javascript-performance-of-property-access-comparing-exp/15

blond commented 8 years ago

In NodeJS performance is better.

benchmark:

var Benchmark = require('benchmark');
var BemEntity = require('bem-entity');

var Benchmark = require('benchmark');
var BemEntity = require('./index.js');

var entity = new BemEntity({ block: 'button', mod: 'disabled' });
var suite = new Benchmark.Suite;

// add tests
suite
.add('direct access', function() {
    entity._obj.mod;
})
.add('function call', function() {
    entity.mmm();
})
.add('readonly property', function() {
    entity.mod;
})
// add listeners
.on('cycle', function(event) {
    console.log(String(event.target));
})
.on('complete', function() {
    console.log('Fastest is ' + this.filter('fastest').map('name'));
})
// run async
.run({ 'async': true });
$ node -v
v4.4.2

$ node ./bench.js

direct access x 80,577,480 ops/sec ±4.30% (78 runs sampled)
function call x 86,146,651 ops/sec ±1.41% (79 runs sampled)
readonly property x 73,289,864 ops/sec ±2.08% (81 runs sampled)

$ node -v
v5.10.1

$ node ./bench.js

direct access x 83,861,168 ops/sec ±2.41% (83 runs sampled)
function call x 85,250,727 ops/sec ±1.71% (78 runs sampled)
readonly property x 73,711,415 ops/sec ±1.45% (81 runs sampled)
blond commented 8 years ago

In addition current interface (with gettres) will allow to save memory.

const BemEntity = require('bem-entity');

const entity1 = new BemEntity({ block: 'button' }); // creates new instance
const entity2 = new BemEntity({ block: 'button' }); // returns previously created instance

entity1 === entity2 // true
blond commented 8 years ago

Update benchmark:

var Benchmark = require('benchmark');
var BemEntity = require('./index.js');

var entity = new BemEntity({ block: 'button', mod: 'disabled' });
var suite = new Benchmark.Suite;

suite
.add('direct access', function() {
    var data = entity._obj.mod;

    return f(data);
})
.add('function call', function() {
    var data = entity.mmm();

    return f(data);
})
.add('readonly property', function() {
    var data = entity.mod;

    return f(data);
})
.on('cycle', function(event) {
    console.log(String(event.target));
})
.on('complete', function() {
    console.log('Fastest is ' + this.filter('fastest').map('name'));
})
.run({ 'async': true });

function f(data) {
    return data + 'abc';
}
$ node -v
v4.4.2

$ node ./bench.js

direct access x 79,371,173 ops/sec ±2.36% (75 runs sampled)
function call x 78,999,689 ops/sec ±1.43% (81 runs sampled)
readonly property x 66,832,962 ops/sec ±1.46% (75 runs sampled)
$ node -v
v5.10.1

$ node ./bench.js

direct access x 73,403,549 ops/sec ±3.67% (75 runs sampled)
function call x 71,923,368 ops/sec ±4.15% (73 runs sampled)
readonly property x 66,553,090 ops/sec ±3.17% (77 runs sampled)
qfox commented 8 years ago

Okay. Looks good torr me