Skip to content

Instantly share code, notes, and snippets.

@snapwich
Last active April 11, 2023 22:50
Show Gist options
  • Star 5 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save snapwich/7604b2d827f320e470a07e088e0293f3 to your computer and use it in GitHub Desktop.
Save snapwich/7604b2d827f320e470a07e088e0293f3 to your computer and use it in GitHub Desktop.
let _ = global._ = require("lodash");
let Benchmark = global.Benchmark = require("benchmark");
let Promise = require("bluebird");
let { Map } = require("immutable");
let { produce } = require("immer");
function getItems(count) {
let id = 1;
return _.times(count, () => ({
name: "city" + id++,
visited: true
}))
}
function assert(val) {
if (!val) {
throw "assertion failed";
}
}
let benchmarks = {
'reduce spread': function(items) {
let initial = {};
const result = items.reduce((accumulator, item) => ({
...accumulator,
[item.name]: item.visited
}), initial);
assert(Object.keys(result).length === items.length);
assert(Object.keys(initial).length === 0);
},
'reduce object.assign': function(items) {
let initial = {};
const result = items.reduce((accumulator, item) =>
Object.assign({}, accumulator, { [item.name]: item.visited}),
initial
);
assert(Object.keys(result).length === items.length);
assert(Object.keys(initial).length === 0);
},
'reduce mutate': function(items) {
let initial = {};
const result = items.reduce((accumulator, item) => {
accumulator[item.name] = item.visited;
return accumulator;
}, initial);
assert(Object.keys(result).length === items.length);
assert(Object.keys(initial).length === items.length); // mutated
},
'object.assign ...map': function(items) {
let result = Object.assign(...items.map(i => ({
[i.name]: i.visited
})));
assert(Object.keys(result).length === items.length);
},
'object.fromEntries ...map': function(items) {
let result = Object.fromEntries(
items.map(({ name, visited }) => [name, visited])
);
assert(Object.keys(result).length === items.length);
},
'reduce immutable.js': function(items) {
let initial = Map({
city0: true
});
let result = items.reduce((accumulator, item) => {
return accumulator.set(item.name, item.visited)
}, initial);
assert(result.size === items.length + 1);
assert(initial.size === 1); // not mutated
},
'reduce immutable.js withMutations': function(items) {
let initial = Map({
city0: true
});
const result = initial.withMutations(initial => items.reduce(
(accumulator, item) => accumulator.set(item.name, item.visited),
initial
));
assert(result.size === items.length + 1);
assert(initial.size === 1); // not mutated
},
'reduce immer.js': function(items) {
let initial = {
city0: true
};
const result = produce(initial, initial => items.reduce(
(accumulator, item) => {
accumulator[item.name] = item.visited;
return accumulator;
},
initial
));
assert(Object.keys(result).length === items.length + 1);
assert(Object.keys(initial).length === 1); // not mutated
},
'for..of': function(items) {
const result = {};
for(let item of items) {
result[item.name] = item.visited;
}
assert(Object.keys(result).length === items.length);
}
};
function runSeries(counts) {
let seriesResults = {};
return counts.map(
count => () => runSuite(count)
.then(results => {
_.forEach(results, (result, name) => {
if (!seriesResults[name]) {
seriesResults[name] = [];
}
seriesResults[name].push([
count,
result
])
})
})
).reduce(
(acc, benchmark) => acc.then(benchmark),
Promise.resolve()
).then(() => seriesResults);
}
function runSuite(count) {
console.log(`benchmark with ${count} items`);
return new Promise((resolve, reject) => {
let items = getItems(count);
let suite = new Benchmark.Suite;
_.forEach(benchmarks, (run, name) => {
suite.add(name, run.bind(null, items),
{
maxTime: 0,
minSamples: 20
}
);
});
suite
.on('error', reject)
.on('cycle', function(event) {
console.log(String(event.target));
})
.on('complete', function() {
console.log('Fastest is ' + this.filter('fastest').map('name'));
resolve(this.reduce((results, benchmark) => {
results[benchmark.name] = Math.round(benchmark.hz)
return results;
}, {}));
})
.run({ async: true });
});
}
runSeries([10, 20, 30, 40, 50, 60, 70, 80, 90, 100]).then(results => {
global.results = results;
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment