perf.js 55 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978
  1. ;(function() {
  2. 'use strict';
  3. /** Used to access the Firebug Lite panel (set by `run`). */
  4. var fbPanel;
  5. /** Used as a safe reference for `undefined` in pre ES5 environments. */
  6. var undefined;
  7. /** Used as a reference to the global object. */
  8. var root = typeof global == 'object' && global || this;
  9. /** Method and object shortcuts. */
  10. var phantom = root.phantom,
  11. amd = root.define && define.amd,
  12. argv = root.process && process.argv,
  13. document = !phantom && root.document,
  14. noop = function() {},
  15. params = root.arguments,
  16. system = root.system;
  17. /** Add `console.log()` support for Rhino and RingoJS. */
  18. var console = root.console || (root.console = { 'log': root.print });
  19. /** The file path of the lodash file to test. */
  20. var filePath = (function() {
  21. var min = 0,
  22. result = [];
  23. if (phantom) {
  24. result = params = phantom.args;
  25. } else if (system) {
  26. min = 1;
  27. result = params = system.args;
  28. } else if (argv) {
  29. min = 2;
  30. result = params = argv;
  31. } else if (params) {
  32. result = params;
  33. }
  34. var last = result[result.length - 1];
  35. result = (result.length > min && !/perf(?:\.js)?$/.test(last)) ? last : '../lodash.js';
  36. if (!amd) {
  37. try {
  38. result = require('fs').realpathSync(result);
  39. } catch (e) {}
  40. try {
  41. result = require.resolve(result);
  42. } catch (e) {}
  43. }
  44. return result;
  45. }());
  46. /** Used to match path separators. */
  47. var rePathSeparator = /[\/\\]/;
  48. /** Used to detect primitive types. */
  49. var rePrimitive = /^(?:boolean|number|string|undefined)$/;
  50. /** Used to match RegExp special characters. */
  51. var reSpecialChars = /[.*+?^=!:${}()|[\]\/\\]/g;
  52. /** The `ui` object. */
  53. var ui = root.ui || (root.ui = {
  54. 'buildPath': basename(filePath, '.js'),
  55. 'otherPath': 'underscore'
  56. });
  57. /** The lodash build basename. */
  58. var buildName = root.buildName = basename(ui.buildPath, '.js');
  59. /** The other library basename. */
  60. var otherName = root.otherName = (function() {
  61. var result = basename(ui.otherPath, '.js');
  62. return result + (result == buildName ? ' (2)' : '');
  63. }());
  64. /** Used to score performance. */
  65. var score = { 'a': [], 'b': [] };
  66. /** Used to queue benchmark suites. */
  67. var suites = [];
  68. /** Use a single "load" function. */
  69. var load = (typeof require == 'function' && !amd)
  70. ? require
  71. : noop;
  72. /** Load lodash. */
  73. var lodash = root.lodash || (root.lodash = (
  74. lodash = load(filePath) || root._,
  75. lodash = lodash._ || lodash,
  76. (lodash.runInContext ? lodash.runInContext(root) : lodash),
  77. lodash.noConflict()
  78. ));
  79. /** Load Underscore. */
  80. var _ = root.underscore || (root.underscore = (
  81. _ = load('../vendor/underscore/underscore.js') || root._,
  82. _._ || _
  83. ));
  84. /** Load Benchmark.js. */
  85. var Benchmark = root.Benchmark || (root.Benchmark = (
  86. Benchmark = load('../node_modules/benchmark/benchmark.js') || root.Benchmark,
  87. Benchmark = Benchmark.Benchmark || Benchmark,
  88. Benchmark.runInContext(lodash.extend({}, root, { '_': lodash }))
  89. ));
  90. /*--------------------------------------------------------------------------*/
  91. /**
  92. * Gets the basename of the given `filePath`. If the file `extension` is passed,
  93. * it will be removed from the basename.
  94. *
  95. * @private
  96. * @param {string} path The file path to inspect.
  97. * @param {string} extension The extension to remove.
  98. * @returns {string} Returns the basename.
  99. */
  100. function basename(filePath, extension) {
  101. var result = (filePath || '').split(rePathSeparator).pop();
  102. return (arguments.length < 2)
  103. ? result
  104. : result.replace(RegExp(extension.replace(reSpecialChars, '\\$&') + '$'), '');
  105. }
  106. /**
  107. * Computes the geometric mean (log-average) of an array of values.
  108. * See http://en.wikipedia.org/wiki/Geometric_mean#Relationship_with_arithmetic_mean_of_logarithms.
  109. *
  110. * @private
  111. * @param {Array} array The array of values.
  112. * @returns {number} The geometric mean.
  113. */
  114. function getGeometricMean(array) {
  115. return Math.pow(Math.E, lodash.reduce(array, function(sum, x) {
  116. return sum + Math.log(x);
  117. }, 0) / array.length) || 0;
  118. }
  119. /**
  120. * Gets the Hz, i.e. operations per second, of `bench` adjusted for the
  121. * margin of error.
  122. *
  123. * @private
  124. * @param {Object} bench The benchmark object.
  125. * @returns {number} Returns the adjusted Hz.
  126. */
  127. function getHz(bench) {
  128. var result = 1 / (bench.stats.mean + bench.stats.moe);
  129. return isFinite(result) ? result : 0;
  130. }
  131. /**
  132. * Host objects can return type values that are different from their actual
  133. * data type. The objects we are concerned with usually return non-primitive
  134. * types of "object", "function", or "unknown".
  135. *
  136. * @private
  137. * @param {*} object The owner of the property.
  138. * @param {string} property The property to check.
  139. * @returns {boolean} Returns `true` if the property value is a non-primitive, else `false`.
  140. */
  141. function isHostType(object, property) {
  142. if (object == null) {
  143. return false;
  144. }
  145. var type = typeof object[property];
  146. return !rePrimitive.test(type) && (type != 'object' || !!object[property]);
  147. }
  148. /**
  149. * Logs text to the console.
  150. *
  151. * @private
  152. * @param {string} text The text to log.
  153. */
  154. function log(text) {
  155. console.log(text + '');
  156. if (fbPanel) {
  157. // Scroll the Firebug Lite panel down.
  158. fbPanel.scrollTop = fbPanel.scrollHeight;
  159. }
  160. }
  161. /**
  162. * Runs all benchmark suites.
  163. *
  164. * @private (@public in the browser)
  165. */
  166. function run() {
  167. fbPanel = (fbPanel = root.document && document.getElementById('FirebugUI')) &&
  168. (fbPanel = (fbPanel = fbPanel.contentWindow || fbPanel.contentDocument).document || fbPanel) &&
  169. fbPanel.getElementById('fbPanel1');
  170. log('\nSit back and relax, this may take a while.');
  171. suites[0].run({ 'async': true });
  172. }
  173. /*--------------------------------------------------------------------------*/
  174. lodash.extend(Benchmark.Suite.options, {
  175. 'onStart': function() {
  176. log('\n' + this.name + ':');
  177. },
  178. 'onCycle': function(event) {
  179. log(event.target);
  180. },
  181. 'onComplete': function() {
  182. for (var index = 0, length = this.length; index < length; index++) {
  183. var bench = this[index];
  184. if (bench.error) {
  185. var errored = true;
  186. }
  187. }
  188. if (errored) {
  189. log('There was a problem, skipping...');
  190. }
  191. else {
  192. var formatNumber = Benchmark.formatNumber,
  193. fastest = this.filter('fastest'),
  194. fastestHz = getHz(fastest[0]),
  195. slowest = this.filter('slowest'),
  196. slowestHz = getHz(slowest[0]),
  197. aHz = getHz(this[0]),
  198. bHz = getHz(this[1]);
  199. if (fastest.length > 1) {
  200. log('It\'s too close to call.');
  201. aHz = bHz = slowestHz;
  202. }
  203. else {
  204. var percent = ((fastestHz / slowestHz) - 1) * 100;
  205. log(
  206. fastest[0].name + ' is ' +
  207. formatNumber(percent < 1 ? percent.toFixed(2) : Math.round(percent)) +
  208. '% faster.'
  209. );
  210. }
  211. // Add score adjusted for margin of error.
  212. score.a.push(aHz);
  213. score.b.push(bHz);
  214. }
  215. // Remove current suite from queue.
  216. suites.shift();
  217. if (suites.length) {
  218. // Run next suite.
  219. suites[0].run({ 'async': true });
  220. }
  221. else {
  222. var aMeanHz = getGeometricMean(score.a),
  223. bMeanHz = getGeometricMean(score.b),
  224. fastestMeanHz = Math.max(aMeanHz, bMeanHz),
  225. slowestMeanHz = Math.min(aMeanHz, bMeanHz),
  226. xFaster = fastestMeanHz / slowestMeanHz,
  227. percentFaster = formatNumber(Math.round((xFaster - 1) * 100)),
  228. message = 'is ' + percentFaster + '% ' + (xFaster == 1 ? '' : '(' + formatNumber(xFaster.toFixed(2)) + 'x) ') + 'faster than';
  229. // Report results.
  230. if (aMeanHz >= bMeanHz) {
  231. log('\n' + buildName + ' ' + message + ' ' + otherName + '.');
  232. } else {
  233. log('\n' + otherName + ' ' + message + ' ' + buildName + '.');
  234. }
  235. }
  236. }
  237. });
  238. /*--------------------------------------------------------------------------*/
  239. lodash.extend(Benchmark.options, {
  240. 'async': true,
  241. 'setup': '\
  242. var _ = global.underscore,\
  243. lodash = global.lodash,\
  244. belt = this.name == buildName ? lodash : _;\
  245. \
  246. var date = new Date,\
  247. limit = 50,\
  248. regexp = /x/,\
  249. object = {},\
  250. objects = Array(limit),\
  251. numbers = Array(limit),\
  252. fourNumbers = [5, 25, 10, 30],\
  253. nestedNumbers = [1, [2], [3, [[4]]]],\
  254. nestedObjects = [{}, [{}], [{}, [[{}]]]],\
  255. twoNumbers = [12, 23];\
  256. \
  257. for (var index = 0; index < limit; index++) {\
  258. numbers[index] = index;\
  259. object["key" + index] = index;\
  260. objects[index] = { "num": index };\
  261. }\
  262. var strNumbers = numbers + "";\
  263. \
  264. if (typeof assign != "undefined") {\
  265. var _assign = _.assign || _.extend,\
  266. lodashAssign = lodash.assign;\
  267. }\
  268. if (typeof bind != "undefined") {\
  269. var thisArg = { "name": "fred" };\
  270. \
  271. var func = function(greeting, punctuation) {\
  272. return (greeting || "hi") + " " + this.name + (punctuation || ".");\
  273. };\
  274. \
  275. var _boundNormal = _.bind(func, thisArg),\
  276. _boundMultiple = _boundNormal,\
  277. _boundPartial = _.bind(func, thisArg, "hi");\
  278. \
  279. var lodashBoundNormal = lodash.bind(func, thisArg),\
  280. lodashBoundMultiple = lodashBoundNormal,\
  281. lodashBoundPartial = lodash.bind(func, thisArg, "hi");\
  282. \
  283. for (index = 0; index < 10; index++) {\
  284. _boundMultiple = _.bind(_boundMultiple, { "name": "fred" + index });\
  285. lodashBoundMultiple = lodash.bind(lodashBoundMultiple, { "name": "fred" + index });\
  286. }\
  287. }\
  288. if (typeof bindAll != "undefined") {\
  289. var bindAllCount = -1,\
  290. bindAllObjects = Array(this.count);\
  291. \
  292. var funcNames = belt.reject(belt.functions(belt).slice(0, 40), function(funcName) {\
  293. return /^_/.test(funcName);\
  294. });\
  295. \
  296. // Potentially expensive.\n\
  297. for (index = 0; index < this.count; index++) {\
  298. bindAllObjects[index] = belt.reduce(funcNames, function(object, funcName) {\
  299. object[funcName] = belt[funcName];\
  300. return object;\
  301. }, {});\
  302. }\
  303. }\
  304. if (typeof chaining != "undefined") {\
  305. var even = function(v) { return v % 2 == 0; },\
  306. square = function(v) { return v * v; };\
  307. \
  308. var largeArray = belt.range(10000),\
  309. _chaining = _(largeArray).chain(),\
  310. lodashChaining = lodash(largeArray).chain();\
  311. }\
  312. if (typeof compact != "undefined") {\
  313. var uncompacted = numbers.slice();\
  314. uncompacted[2] = false;\
  315. uncompacted[6] = null;\
  316. uncompacted[18] = "";\
  317. }\
  318. if (typeof flowRight != "undefined") {\
  319. var compAddOne = function(n) { return n + 1; },\
  320. compAddTwo = function(n) { return n + 2; },\
  321. compAddThree = function(n) { return n + 3; };\
  322. \
  323. var _composed = _.flowRight && _.flowRight(compAddThree, compAddTwo, compAddOne),\
  324. lodashComposed = lodash.flowRight && lodash.flowRight(compAddThree, compAddTwo, compAddOne);\
  325. }\
  326. if (typeof countBy != "undefined" || typeof omit != "undefined") {\
  327. var wordToNumber = {\
  328. "one": 1,\
  329. "two": 2,\
  330. "three": 3,\
  331. "four": 4,\
  332. "five": 5,\
  333. "six": 6,\
  334. "seven": 7,\
  335. "eight": 8,\
  336. "nine": 9,\
  337. "ten": 10,\
  338. "eleven": 11,\
  339. "twelve": 12,\
  340. "thirteen": 13,\
  341. "fourteen": 14,\
  342. "fifteen": 15,\
  343. "sixteen": 16,\
  344. "seventeen": 17,\
  345. "eighteen": 18,\
  346. "nineteen": 19,\
  347. "twenty": 20,\
  348. "twenty-one": 21,\
  349. "twenty-two": 22,\
  350. "twenty-three": 23,\
  351. "twenty-four": 24,\
  352. "twenty-five": 25,\
  353. "twenty-six": 26,\
  354. "twenty-seven": 27,\
  355. "twenty-eight": 28,\
  356. "twenty-nine": 29,\
  357. "thirty": 30,\
  358. "thirty-one": 31,\
  359. "thirty-two": 32,\
  360. "thirty-three": 33,\
  361. "thirty-four": 34,\
  362. "thirty-five": 35,\
  363. "thirty-six": 36,\
  364. "thirty-seven": 37,\
  365. "thirty-eight": 38,\
  366. "thirty-nine": 39,\
  367. "forty": 40\
  368. };\
  369. \
  370. var words = belt.keys(wordToNumber).slice(0, limit);\
  371. }\
  372. if (typeof flatten != "undefined") {\
  373. var _flattenDeep = _.flatten([[1]])[0] !== 1,\
  374. lodashFlattenDeep = lodash.flatten([[1]])[0] !== 1;\
  375. }\
  376. if (typeof isEqual != "undefined") {\
  377. var objectOfPrimitives = {\
  378. "boolean": true,\
  379. "number": 1,\
  380. "string": "a"\
  381. };\
  382. \
  383. var objectOfObjects = {\
  384. "boolean": new Boolean(true),\
  385. "number": new Number(1),\
  386. "string": new String("a")\
  387. };\
  388. \
  389. var objectOfObjects2 = {\
  390. "boolean": new Boolean(true),\
  391. "number": new Number(1),\
  392. "string": new String("A")\
  393. };\
  394. \
  395. var object2 = {},\
  396. object3 = {},\
  397. objects2 = Array(limit),\
  398. objects3 = Array(limit),\
  399. numbers2 = Array(limit),\
  400. numbers3 = Array(limit),\
  401. nestedNumbers2 = [1, [2], [3, [[4]]]],\
  402. nestedNumbers3 = [1, [2], [3, [[6]]]];\
  403. \
  404. for (index = 0; index < limit; index++) {\
  405. object2["key" + index] = index;\
  406. object3["key" + index] = index;\
  407. objects2[index] = { "num": index };\
  408. objects3[index] = { "num": index };\
  409. numbers2[index] = index;\
  410. numbers3[index] = index;\
  411. }\
  412. object3["key" + (limit - 1)] = -1;\
  413. objects3[limit - 1].num = -1;\
  414. numbers3[limit - 1] = -1;\
  415. }\
  416. if (typeof matches != "undefined") {\
  417. var source = { "num": 9 };\
  418. \
  419. var _matcher = (_.matches || _.noop)(source),\
  420. lodashMatcher = (lodash.matches || lodash.noop)(source);\
  421. }\
  422. if (typeof multiArrays != "undefined") {\
  423. var twentyValues = belt.shuffle(belt.range(20)),\
  424. fortyValues = belt.shuffle(belt.range(40)),\
  425. hundredSortedValues = belt.range(100),\
  426. hundredValues = belt.shuffle(hundredSortedValues),\
  427. hundredValues2 = belt.shuffle(hundredValues),\
  428. hundredTwentyValues = belt.shuffle(belt.range(120)),\
  429. hundredTwentyValues2 = belt.shuffle(hundredTwentyValues),\
  430. twoHundredValues = belt.shuffle(belt.range(200)),\
  431. twoHundredValues2 = belt.shuffle(twoHundredValues);\
  432. }\
  433. if (typeof partial != "undefined") {\
  434. var func = function(greeting, punctuation) {\
  435. return greeting + " fred" + (punctuation || ".");\
  436. };\
  437. \
  438. var _partial = _.partial(func, "hi"),\
  439. lodashPartial = lodash.partial(func, "hi");\
  440. }\
  441. if (typeof template != "undefined") {\
  442. var tplData = {\
  443. "header1": "Header1",\
  444. "header2": "Header2",\
  445. "header3": "Header3",\
  446. "header4": "Header4",\
  447. "header5": "Header5",\
  448. "header6": "Header6",\
  449. "list": ["1", "2", "3", "4", "5", "6", "7", "8", "9", "10"]\
  450. };\
  451. \
  452. var tpl =\
  453. "<div>" +\
  454. "<h1 class=\'header1\'><%= header1 %></h1>" +\
  455. "<h2 class=\'header2\'><%= header2 %></h2>" +\
  456. "<h3 class=\'header3\'><%= header3 %></h3>" +\
  457. "<h4 class=\'header4\'><%= header4 %></h4>" +\
  458. "<h5 class=\'header5\'><%= header5 %></h5>" +\
  459. "<h6 class=\'header6\'><%= header6 %></h6>" +\
  460. "<ul class=\'list\'>" +\
  461. "<% for (var index = 0, length = list.length; index < length; index++) { %>" +\
  462. "<li class=\'item\'><%= list[index] %></li>" +\
  463. "<% } %>" +\
  464. "</ul>" +\
  465. "</div>";\
  466. \
  467. var tplVerbose =\
  468. "<div>" +\
  469. "<h1 class=\'header1\'><%= data.header1 %></h1>" +\
  470. "<h2 class=\'header2\'><%= data.header2 %></h2>" +\
  471. "<h3 class=\'header3\'><%= data.header3 %></h3>" +\
  472. "<h4 class=\'header4\'><%= data.header4 %></h4>" +\
  473. "<h5 class=\'header5\'><%= data.header5 %></h5>" +\
  474. "<h6 class=\'header6\'><%= data.header6 %></h6>" +\
  475. "<ul class=\'list\'>" +\
  476. "<% for (var index = 0, length = data.list.length; index < length; index++) { %>" +\
  477. "<li class=\'item\'><%= data.list[index] %></li>" +\
  478. "<% } %>" +\
  479. "</ul>" +\
  480. "</div>";\
  481. \
  482. var settingsObject = { "variable": "data" };\
  483. \
  484. var _tpl = _.template(tpl),\
  485. _tplVerbose = _.template(tplVerbose, null, settingsObject);\
  486. \
  487. var lodashTpl = lodash.template(tpl),\
  488. lodashTplVerbose = lodash.template(tplVerbose, null, settingsObject);\
  489. }\
  490. if (typeof wrap != "undefined") {\
  491. var add = function(a, b) {\
  492. return a + b;\
  493. };\
  494. \
  495. var average = function(func, a, b) {\
  496. return (func(a, b) / 2).toFixed(2);\
  497. };\
  498. \
  499. var _wrapped = _.wrap(add, average);\
  500. lodashWrapped = lodash.wrap(add, average);\
  501. }\
  502. if (typeof zip != "undefined") {\
  503. var unzipped = [["a", "b", "c"], [1, 2, 3], [true, false, true]];\
  504. }'
  505. });
  506. /*--------------------------------------------------------------------------*/
  507. suites.push(
  508. Benchmark.Suite('`_(...).map(...).filter(...).take(...).value()`')
  509. .add(buildName, {
  510. 'fn': 'lodashChaining.map(square).filter(even).take(100).value()',
  511. 'teardown': 'function chaining(){}'
  512. })
  513. .add(otherName, {
  514. 'fn': '_chaining.map(square).filter(even).take(100).value()',
  515. 'teardown': 'function chaining(){}'
  516. })
  517. );
  518. /*--------------------------------------------------------------------------*/
  519. suites.push(
  520. Benchmark.Suite('`_.assign`')
  521. .add(buildName, {
  522. 'fn': 'lodashAssign({}, { "a": 1, "b": 2, "c": 3 })',
  523. 'teardown': 'function assign(){}'
  524. })
  525. .add(otherName, {
  526. 'fn': '_assign({}, { "a": 1, "b": 2, "c": 3 })',
  527. 'teardown': 'function assign(){}'
  528. })
  529. );
  530. suites.push(
  531. Benchmark.Suite('`_.assign` with multiple sources')
  532. .add(buildName, {
  533. 'fn': 'lodashAssign({}, { "a": 1, "b": 2 }, { "c": 3, "d": 4 })',
  534. 'teardown': 'function assign(){}'
  535. })
  536. .add(otherName, {
  537. 'fn': '_assign({}, { "a": 1, "b": 2 }, { "c": 3, "d": 4 })',
  538. 'teardown': 'function assign(){}'
  539. })
  540. );
  541. /*--------------------------------------------------------------------------*/
  542. suites.push(
  543. Benchmark.Suite('`_.bind` (slow path)')
  544. .add(buildName, {
  545. 'fn': 'lodash.bind(function() { return this.name; }, { "name": "fred" })',
  546. 'teardown': 'function bind(){}'
  547. })
  548. .add(otherName, {
  549. 'fn': '_.bind(function() { return this.name; }, { "name": "fred" })',
  550. 'teardown': 'function bind(){}'
  551. })
  552. );
  553. suites.push(
  554. Benchmark.Suite('bound call with arguments')
  555. .add(buildName, {
  556. 'fn': 'lodashBoundNormal("hi", "!")',
  557. 'teardown': 'function bind(){}'
  558. })
  559. .add(otherName, {
  560. 'fn': '_boundNormal("hi", "!")',
  561. 'teardown': 'function bind(){}'
  562. })
  563. );
  564. suites.push(
  565. Benchmark.Suite('bound and partially applied call with arguments')
  566. .add(buildName, {
  567. 'fn': 'lodashBoundPartial("!")',
  568. 'teardown': 'function bind(){}'
  569. })
  570. .add(otherName, {
  571. 'fn': '_boundPartial("!")',
  572. 'teardown': 'function bind(){}'
  573. })
  574. );
  575. suites.push(
  576. Benchmark.Suite('bound multiple times')
  577. .add(buildName, {
  578. 'fn': 'lodashBoundMultiple()',
  579. 'teardown': 'function bind(){}'
  580. })
  581. .add(otherName, {
  582. 'fn': '_boundMultiple()',
  583. 'teardown': 'function bind(){}'
  584. })
  585. );
  586. /*--------------------------------------------------------------------------*/
  587. suites.push(
  588. Benchmark.Suite('`_.bindAll`')
  589. .add(buildName, {
  590. 'fn': 'lodash.bindAll(bindAllObjects[++bindAllCount], funcNames)',
  591. 'teardown': 'function bindAll(){}'
  592. })
  593. .add(otherName, {
  594. 'fn': '_.bindAll(bindAllObjects[++bindAllCount], funcNames)',
  595. 'teardown': 'function bindAll(){}'
  596. })
  597. );
  598. /*--------------------------------------------------------------------------*/
  599. suites.push(
  600. Benchmark.Suite('`_.clone` with an array')
  601. .add(buildName, '\
  602. lodash.clone(numbers)'
  603. )
  604. .add(otherName, '\
  605. _.clone(numbers)'
  606. )
  607. );
  608. suites.push(
  609. Benchmark.Suite('`_.clone` with an object')
  610. .add(buildName, '\
  611. lodash.clone(object)'
  612. )
  613. .add(otherName, '\
  614. _.clone(object)'
  615. )
  616. );
  617. /*--------------------------------------------------------------------------*/
  618. suites.push(
  619. Benchmark.Suite('`_.compact`')
  620. .add(buildName, {
  621. 'fn': 'lodash.compact(uncompacted)',
  622. 'teardown': 'function compact(){}'
  623. })
  624. .add(otherName, {
  625. 'fn': '_.compact(uncompacted)',
  626. 'teardown': 'function compact(){}'
  627. })
  628. );
  629. /*--------------------------------------------------------------------------*/
  630. suites.push(
  631. Benchmark.Suite('`_.countBy` with `callback` iterating an array')
  632. .add(buildName, '\
  633. lodash.countBy(numbers, function(num) { return num >> 1; })'
  634. )
  635. .add(otherName, '\
  636. _.countBy(numbers, function(num) { return num >> 1; })'
  637. )
  638. );
  639. suites.push(
  640. Benchmark.Suite('`_.countBy` with `property` name iterating an array')
  641. .add(buildName, {
  642. 'fn': 'lodash.countBy(words, "length")',
  643. 'teardown': 'function countBy(){}'
  644. })
  645. .add(otherName, {
  646. 'fn': '_.countBy(words, "length")',
  647. 'teardown': 'function countBy(){}'
  648. })
  649. );
  650. suites.push(
  651. Benchmark.Suite('`_.countBy` with `callback` iterating an object')
  652. .add(buildName, {
  653. 'fn': 'lodash.countBy(wordToNumber, function(num) { return num >> 1; })',
  654. 'teardown': 'function countBy(){}'
  655. })
  656. .add(otherName, {
  657. 'fn': '_.countBy(wordToNumber, function(num) { return num >> 1; })',
  658. 'teardown': 'function countBy(){}'
  659. })
  660. );
  661. /*--------------------------------------------------------------------------*/
  662. suites.push(
  663. Benchmark.Suite('`_.defaults`')
  664. .add(buildName, '\
  665. lodash.defaults({ "key2": 2, "key6": 6, "key18": 18 }, object)'
  666. )
  667. .add(otherName, '\
  668. _.defaults({ "key2": 2, "key6": 6, "key18": 18 }, object)'
  669. )
  670. );
  671. /*--------------------------------------------------------------------------*/
  672. suites.push(
  673. Benchmark.Suite('`_.difference`')
  674. .add(buildName, '\
  675. lodash.difference(numbers, twoNumbers, fourNumbers)'
  676. )
  677. .add(otherName, '\
  678. _.difference(numbers, twoNumbers, fourNumbers)'
  679. )
  680. );
  681. suites.push(
  682. Benchmark.Suite('`_.difference` iterating 20 and 40 elements')
  683. .add(buildName, {
  684. 'fn': 'lodash.difference(twentyValues, fortyValues)',
  685. 'teardown': 'function multiArrays(){}'
  686. })
  687. .add(otherName, {
  688. 'fn': '_.difference(twentyValues, fortyValues)',
  689. 'teardown': 'function multiArrays(){}'
  690. })
  691. );
  692. suites.push(
  693. Benchmark.Suite('`_.difference` iterating 200 elements')
  694. .add(buildName, {
  695. 'fn': 'lodash.difference(twoHundredValues, twoHundredValues2)',
  696. 'teardown': 'function multiArrays(){}'
  697. })
  698. .add(otherName, {
  699. 'fn': '_.difference(twoHundredValues, twoHundredValues2)',
  700. 'teardown': 'function multiArrays(){}'
  701. })
  702. );
  703. /*--------------------------------------------------------------------------*/
  704. suites.push(
  705. Benchmark.Suite('`_.each` iterating an array')
  706. .add(buildName, '\
  707. var result = [];\
  708. lodash.each(numbers, function(num) {\
  709. result.push(num * 2);\
  710. })'
  711. )
  712. .add(otherName, '\
  713. var result = [];\
  714. _.each(numbers, function(num) {\
  715. result.push(num * 2);\
  716. })'
  717. )
  718. );
  719. suites.push(
  720. Benchmark.Suite('`_.each` iterating an object')
  721. .add(buildName, '\
  722. var result = [];\
  723. lodash.each(object, function(num) {\
  724. result.push(num * 2);\
  725. })'
  726. )
  727. .add(otherName, '\
  728. var result = [];\
  729. _.each(object, function(num) {\
  730. result.push(num * 2);\
  731. })'
  732. )
  733. );
  734. /*--------------------------------------------------------------------------*/
  735. suites.push(
  736. Benchmark.Suite('`_.every` iterating an array')
  737. .add(buildName, '\
  738. lodash.every(numbers, function(num) {\
  739. return num < limit;\
  740. })'
  741. )
  742. .add(otherName, '\
  743. _.every(numbers, function(num) {\
  744. return num < limit;\
  745. })'
  746. )
  747. );
  748. suites.push(
  749. Benchmark.Suite('`_.every` iterating an object')
  750. .add(buildName, '\
  751. lodash.every(object, function(num) {\
  752. return num < limit;\
  753. })'
  754. )
  755. .add(otherName, '\
  756. _.every(object, function(num) {\
  757. return num < limit;\
  758. })'
  759. )
  760. );
  761. /*--------------------------------------------------------------------------*/
  762. suites.push(
  763. Benchmark.Suite('`_.filter` iterating an array')
  764. .add(buildName, '\
  765. lodash.filter(numbers, function(num) {\
  766. return num % 2;\
  767. })'
  768. )
  769. .add(otherName, '\
  770. _.filter(numbers, function(num) {\
  771. return num % 2;\
  772. })'
  773. )
  774. );
  775. suites.push(
  776. Benchmark.Suite('`_.filter` iterating an object')
  777. .add(buildName, '\
  778. lodash.filter(object, function(num) {\
  779. return num % 2\
  780. })'
  781. )
  782. .add(otherName, '\
  783. _.filter(object, function(num) {\
  784. return num % 2\
  785. })'
  786. )
  787. );
  788. suites.push(
  789. Benchmark.Suite('`_.filter` with `_.matches` shorthand')
  790. .add(buildName, {
  791. 'fn': 'lodash.filter(objects, source)',
  792. 'teardown': 'function matches(){}'
  793. })
  794. .add(otherName, {
  795. 'fn': '_.filter(objects, source)',
  796. 'teardown': 'function matches(){}'
  797. })
  798. );
  799. suites.push(
  800. Benchmark.Suite('`_.filter` with `_.matches` predicate')
  801. .add(buildName, {
  802. 'fn': 'lodash.filter(objects, lodashMatcher)',
  803. 'teardown': 'function matches(){}'
  804. })
  805. .add(otherName, {
  806. 'fn': '_.filter(objects, _matcher)',
  807. 'teardown': 'function matches(){}'
  808. })
  809. );
  810. /*--------------------------------------------------------------------------*/
  811. suites.push(
  812. Benchmark.Suite('`_.find` iterating an array')
  813. .add(buildName, '\
  814. lodash.find(numbers, function(num) {\
  815. return num === (limit - 1);\
  816. })'
  817. )
  818. .add(otherName, '\
  819. _.find(numbers, function(num) {\
  820. return num === (limit - 1);\
  821. })'
  822. )
  823. );
  824. suites.push(
  825. Benchmark.Suite('`_.find` iterating an object')
  826. .add(buildName, '\
  827. lodash.find(object, function(value, key) {\
  828. return /\D9$/.test(key);\
  829. })'
  830. )
  831. .add(otherName, '\
  832. _.find(object, function(value, key) {\
  833. return /\D9$/.test(key);\
  834. })'
  835. )
  836. );
  837. // Avoid Underscore induced `OutOfMemoryError` in Rhino and Ringo.
  838. suites.push(
  839. Benchmark.Suite('`_.find` with `_.matches` shorthand')
  840. .add(buildName, {
  841. 'fn': 'lodash.find(objects, source)',
  842. 'teardown': 'function matches(){}'
  843. })
  844. .add(otherName, {
  845. 'fn': '_.find(objects, source)',
  846. 'teardown': 'function matches(){}'
  847. })
  848. );
  849. /*--------------------------------------------------------------------------*/
  850. suites.push(
  851. Benchmark.Suite('`_.flatten`')
  852. .add(buildName, {
  853. 'fn': 'lodash.flatten(nestedNumbers, !lodashFlattenDeep)',
  854. 'teardown': 'function flatten(){}'
  855. })
  856. .add(otherName, {
  857. 'fn': '_.flatten(nestedNumbers, !_flattenDeep)',
  858. 'teardown': 'function flatten(){}'
  859. })
  860. );
  861. /*--------------------------------------------------------------------------*/
  862. suites.push(
  863. Benchmark.Suite('`_.flattenDeep` nested arrays of numbers')
  864. .add(buildName, {
  865. 'fn': 'lodash.flattenDeep(nestedNumbers)',
  866. 'teardown': 'function flatten(){}'
  867. })
  868. .add(otherName, {
  869. 'fn': '_.flattenDeep(nestedNumbers)',
  870. 'teardown': 'function flatten(){}'
  871. })
  872. );
  873. suites.push(
  874. Benchmark.Suite('`_.flattenDeep` nest arrays of objects')
  875. .add(buildName, {
  876. 'fn': 'lodash.flattenDeep(nestedObjects)',
  877. 'teardown': 'function flatten(){}'
  878. })
  879. .add(otherName, {
  880. 'fn': '_.flattenDeep(nestedObjects)',
  881. 'teardown': 'function flatten(){}'
  882. })
  883. );
  884. /*--------------------------------------------------------------------------*/
  885. suites.push(
  886. Benchmark.Suite('`_.flowRight`')
  887. .add(buildName, {
  888. 'fn': 'lodash.flowRight(compAddThree, compAddTwo, compAddOne)',
  889. 'teardown': 'function flowRight(){}'
  890. })
  891. .add(otherName, {
  892. 'fn': '_.flowRight(compAddThree, compAddTwo, compAddOne)',
  893. 'teardown': 'function flowRight(){}'
  894. })
  895. );
  896. suites.push(
  897. Benchmark.Suite('composed call')
  898. .add(buildName, {
  899. 'fn': 'lodashComposed(0)',
  900. 'teardown': 'function flowRight(){}'
  901. })
  902. .add(otherName, {
  903. 'fn': '_composed(0)',
  904. 'teardown': 'function flowRight(){}'
  905. })
  906. );
  907. /*--------------------------------------------------------------------------*/
  908. suites.push(
  909. Benchmark.Suite('`_.functions`')
  910. .add(buildName, '\
  911. lodash.functions(lodash)'
  912. )
  913. .add(otherName, '\
  914. _.functions(lodash)'
  915. )
  916. );
  917. /*--------------------------------------------------------------------------*/
  918. suites.push(
  919. Benchmark.Suite('`_.groupBy` with `callback` iterating an array')
  920. .add(buildName, '\
  921. lodash.groupBy(numbers, function(num) { return num >> 1; })'
  922. )
  923. .add(otherName, '\
  924. _.groupBy(numbers, function(num) { return num >> 1; })'
  925. )
  926. );
  927. suites.push(
  928. Benchmark.Suite('`_.groupBy` with `property` name iterating an array')
  929. .add(buildName, {
  930. 'fn': 'lodash.groupBy(words, "length")',
  931. 'teardown': 'function countBy(){}'
  932. })
  933. .add(otherName, {
  934. 'fn': '_.groupBy(words, "length")',
  935. 'teardown': 'function countBy(){}'
  936. })
  937. );
  938. suites.push(
  939. Benchmark.Suite('`_.groupBy` with `callback` iterating an object')
  940. .add(buildName, {
  941. 'fn': 'lodash.groupBy(wordToNumber, function(num) { return num >> 1; })',
  942. 'teardown': 'function countBy(){}'
  943. })
  944. .add(otherName, {
  945. 'fn': '_.groupBy(wordToNumber, function(num) { return num >> 1; })',
  946. 'teardown': 'function countBy(){}'
  947. })
  948. );
  949. /*--------------------------------------------------------------------------*/
  950. suites.push(
  951. Benchmark.Suite('`_.includes` searching an array')
  952. .add(buildName, '\
  953. lodash.includes(numbers, limit - 1)'
  954. )
  955. .add(otherName, '\
  956. _.includes(numbers, limit - 1)'
  957. )
  958. );
  959. suites.push(
  960. Benchmark.Suite('`_.includes` searching an object')
  961. .add(buildName, '\
  962. lodash.includes(object, limit - 1)'
  963. )
  964. .add(otherName, '\
  965. _.includes(object, limit - 1)'
  966. )
  967. );
  968. if (lodash.includes('ab', 'ab') && _.includes('ab', 'ab')) {
  969. suites.push(
  970. Benchmark.Suite('`_.includes` searching a string')
  971. .add(buildName, '\
  972. lodash.includes(strNumbers, "," + (limit - 1))'
  973. )
  974. .add(otherName, '\
  975. _.includes(strNumbers, "," + (limit - 1))'
  976. )
  977. );
  978. }
  979. /*--------------------------------------------------------------------------*/
  980. suites.push(
  981. Benchmark.Suite('`_.indexOf`')
  982. .add(buildName, {
  983. 'fn': 'lodash.indexOf(hundredSortedValues, 99)',
  984. 'teardown': 'function multiArrays(){}'
  985. })
  986. .add(otherName, {
  987. 'fn': '_.indexOf(hundredSortedValues, 99)',
  988. 'teardown': 'function multiArrays(){}'
  989. })
  990. );
  991. /*--------------------------------------------------------------------------*/
  992. suites.push(
  993. Benchmark.Suite('`_.intersection`')
  994. .add(buildName, '\
  995. lodash.intersection(numbers, twoNumbers, fourNumbers)'
  996. )
  997. .add(otherName, '\
  998. _.intersection(numbers, twoNumbers, fourNumbers)'
  999. )
  1000. );
  1001. suites.push(
  1002. Benchmark.Suite('`_.intersection` iterating 120 elements')
  1003. .add(buildName, {
  1004. 'fn': 'lodash.intersection(hundredTwentyValues, hundredTwentyValues2)',
  1005. 'teardown': 'function multiArrays(){}'
  1006. })
  1007. .add(otherName, {
  1008. 'fn': '_.intersection(hundredTwentyValues, hundredTwentyValues2)',
  1009. 'teardown': 'function multiArrays(){}'
  1010. })
  1011. );
  1012. /*--------------------------------------------------------------------------*/
  1013. suites.push(
  1014. Benchmark.Suite('`_.invert`')
  1015. .add(buildName, '\
  1016. lodash.invert(object)'
  1017. )
  1018. .add(otherName, '\
  1019. _.invert(object)'
  1020. )
  1021. );
  1022. /*--------------------------------------------------------------------------*/
  1023. suites.push(
  1024. Benchmark.Suite('`_.invokeMap` iterating an array')
  1025. .add(buildName, '\
  1026. lodash.invokeMap(numbers, "toFixed")'
  1027. )
  1028. .add(otherName, '\
  1029. _.invokeMap(numbers, "toFixed")'
  1030. )
  1031. );
  1032. suites.push(
  1033. Benchmark.Suite('`_.invokeMap` with arguments iterating an array')
  1034. .add(buildName, '\
  1035. lodash.invokeMap(numbers, "toFixed", 1)'
  1036. )
  1037. .add(otherName, '\
  1038. _.invokeMap(numbers, "toFixed", 1)'
  1039. )
  1040. );
  1041. suites.push(
  1042. Benchmark.Suite('`_.invokeMap` with a function for `path` iterating an array')
  1043. .add(buildName, '\
  1044. lodash.invokeMap(numbers, Number.prototype.toFixed, 1)'
  1045. )
  1046. .add(otherName, '\
  1047. _.invokeMap(numbers, Number.prototype.toFixed, 1)'
  1048. )
  1049. );
  1050. suites.push(
  1051. Benchmark.Suite('`_.invokeMap` iterating an object')
  1052. .add(buildName, '\
  1053. lodash.invokeMap(object, "toFixed", 1)'
  1054. )
  1055. .add(otherName, '\
  1056. _.invokeMap(object, "toFixed", 1)'
  1057. )
  1058. );
  1059. /*--------------------------------------------------------------------------*/
  1060. suites.push(
  1061. Benchmark.Suite('`_.isEqual` comparing primitives')
  1062. .add(buildName, {
  1063. 'fn': '\
  1064. lodash.isEqual(1, "1");\
  1065. lodash.isEqual(1, 1)',
  1066. 'teardown': 'function isEqual(){}'
  1067. })
  1068. .add(otherName, {
  1069. 'fn': '\
  1070. _.isEqual(1, "1");\
  1071. _.isEqual(1, 1);',
  1072. 'teardown': 'function isEqual(){}'
  1073. })
  1074. );
  1075. suites.push(
  1076. Benchmark.Suite('`_.isEqual` comparing primitives and their object counterparts (edge case)')
  1077. .add(buildName, {
  1078. 'fn': '\
  1079. lodash.isEqual(objectOfPrimitives, objectOfObjects);\
  1080. lodash.isEqual(objectOfPrimitives, objectOfObjects2)',
  1081. 'teardown': 'function isEqual(){}'
  1082. })
  1083. .add(otherName, {
  1084. 'fn': '\
  1085. _.isEqual(objectOfPrimitives, objectOfObjects);\
  1086. _.isEqual(objectOfPrimitives, objectOfObjects2)',
  1087. 'teardown': 'function isEqual(){}'
  1088. })
  1089. );
  1090. suites.push(
  1091. Benchmark.Suite('`_.isEqual` comparing arrays')
  1092. .add(buildName, {
  1093. 'fn': '\
  1094. lodash.isEqual(numbers, numbers2);\
  1095. lodash.isEqual(numbers2, numbers3)',
  1096. 'teardown': 'function isEqual(){}'
  1097. })
  1098. .add(otherName, {
  1099. 'fn': '\
  1100. _.isEqual(numbers, numbers2);\
  1101. _.isEqual(numbers2, numbers3)',
  1102. 'teardown': 'function isEqual(){}'
  1103. })
  1104. );
  1105. suites.push(
  1106. Benchmark.Suite('`_.isEqual` comparing nested arrays')
  1107. .add(buildName, {
  1108. 'fn': '\
  1109. lodash.isEqual(nestedNumbers, nestedNumbers2);\
  1110. lodash.isEqual(nestedNumbers2, nestedNumbers3)',
  1111. 'teardown': 'function isEqual(){}'
  1112. })
  1113. .add(otherName, {
  1114. 'fn': '\
  1115. _.isEqual(nestedNumbers, nestedNumbers2);\
  1116. _.isEqual(nestedNumbers2, nestedNumbers3)',
  1117. 'teardown': 'function isEqual(){}'
  1118. })
  1119. );
  1120. suites.push(
  1121. Benchmark.Suite('`_.isEqual` comparing arrays of objects')
  1122. .add(buildName, {
  1123. 'fn': '\
  1124. lodash.isEqual(objects, objects2);\
  1125. lodash.isEqual(objects2, objects3)',
  1126. 'teardown': 'function isEqual(){}'
  1127. })
  1128. .add(otherName, {
  1129. 'fn': '\
  1130. _.isEqual(objects, objects2);\
  1131. _.isEqual(objects2, objects3)',
  1132. 'teardown': 'function isEqual(){}'
  1133. })
  1134. );
  1135. suites.push(
  1136. Benchmark.Suite('`_.isEqual` comparing objects')
  1137. .add(buildName, {
  1138. 'fn': '\
  1139. lodash.isEqual(object, object2);\
  1140. lodash.isEqual(object2, object3)',
  1141. 'teardown': 'function isEqual(){}'
  1142. })
  1143. .add(otherName, {
  1144. 'fn': '\
  1145. _.isEqual(object, object2);\
  1146. _.isEqual(object2, object3)',
  1147. 'teardown': 'function isEqual(){}'
  1148. })
  1149. );
  1150. /*--------------------------------------------------------------------------*/
  1151. suites.push(
  1152. Benchmark.Suite('`_.isArguments`, `_.isDate`, `_.isFunction`, `_.isNumber`, `_.isObject`, `_.isRegExp`')
  1153. .add(buildName, '\
  1154. lodash.isArguments(arguments);\
  1155. lodash.isArguments(object);\
  1156. lodash.isDate(date);\
  1157. lodash.isDate(object);\
  1158. lodash.isFunction(lodash);\
  1159. lodash.isFunction(object);\
  1160. lodash.isNumber(1);\
  1161. lodash.isNumber(object);\
  1162. lodash.isObject(object);\
  1163. lodash.isObject(1);\
  1164. lodash.isRegExp(regexp);\
  1165. lodash.isRegExp(object)'
  1166. )
  1167. .add(otherName, '\
  1168. _.isArguments(arguments);\
  1169. _.isArguments(object);\
  1170. _.isDate(date);\
  1171. _.isDate(object);\
  1172. _.isFunction(_);\
  1173. _.isFunction(object);\
  1174. _.isNumber(1);\
  1175. _.isNumber(object);\
  1176. _.isObject(object);\
  1177. _.isObject(1);\
  1178. _.isRegExp(regexp);\
  1179. _.isRegExp(object)'
  1180. )
  1181. );
  1182. /*--------------------------------------------------------------------------*/
  1183. suites.push(
  1184. Benchmark.Suite('`_.keys` (uses native `Object.keys` if available)')
  1185. .add(buildName, '\
  1186. lodash.keys(object)'
  1187. )
  1188. .add(otherName, '\
  1189. _.keys(object)'
  1190. )
  1191. );
  1192. /*--------------------------------------------------------------------------*/
  1193. suites.push(
  1194. Benchmark.Suite('`_.lastIndexOf`')
  1195. .add(buildName, {
  1196. 'fn': 'lodash.lastIndexOf(hundredSortedValues, 0)',
  1197. 'teardown': 'function multiArrays(){}'
  1198. })
  1199. .add(otherName, {
  1200. 'fn': '_.lastIndexOf(hundredSortedValues, 0)',
  1201. 'teardown': 'function multiArrays(){}'
  1202. })
  1203. );
  1204. /*--------------------------------------------------------------------------*/
  1205. suites.push(
  1206. Benchmark.Suite('`_.map` iterating an array')
  1207. .add(buildName, '\
  1208. lodash.map(objects, function(value) {\
  1209. return value.num;\
  1210. })'
  1211. )
  1212. .add(otherName, '\
  1213. _.map(objects, function(value) {\
  1214. return value.num;\
  1215. })'
  1216. )
  1217. );
  1218. suites.push(
  1219. Benchmark.Suite('`_.map` iterating an object')
  1220. .add(buildName, '\
  1221. lodash.map(object, function(value) {\
  1222. return value;\
  1223. })'
  1224. )
  1225. .add(otherName, '\
  1226. _.map(object, function(value) {\
  1227. return value;\
  1228. })'
  1229. )
  1230. );
  1231. suites.push(
  1232. Benchmark.Suite('`_.map` with `_.property` shorthand')
  1233. .add(buildName, '\
  1234. lodash.map(objects, "num")'
  1235. )
  1236. .add(otherName, '\
  1237. _.map(objects, "num")'
  1238. )
  1239. );
  1240. /*--------------------------------------------------------------------------*/
  1241. suites.push(
  1242. Benchmark.Suite('`_.max`')
  1243. .add(buildName, '\
  1244. lodash.max(numbers)'
  1245. )
  1246. .add(otherName, '\
  1247. _.max(numbers)'
  1248. )
  1249. );
  1250. /*--------------------------------------------------------------------------*/
  1251. suites.push(
  1252. Benchmark.Suite('`_.min`')
  1253. .add(buildName, '\
  1254. lodash.min(numbers)'
  1255. )
  1256. .add(otherName, '\
  1257. _.min(numbers)'
  1258. )
  1259. );
  1260. /*--------------------------------------------------------------------------*/
  1261. suites.push(
  1262. Benchmark.Suite('`_.omit` iterating 20 properties, omitting 2 keys')
  1263. .add(buildName, '\
  1264. lodash.omit(object, "key6", "key13")'
  1265. )
  1266. .add(otherName, '\
  1267. _.omit(object, "key6", "key13")'
  1268. )
  1269. );
  1270. suites.push(
  1271. Benchmark.Suite('`_.omit` iterating 40 properties, omitting 20 keys')
  1272. .add(buildName, {
  1273. 'fn': 'lodash.omit(wordToNumber, words)',
  1274. 'teardown': 'function omit(){}'
  1275. })
  1276. .add(otherName, {
  1277. 'fn': '_.omit(wordToNumber, words)',
  1278. 'teardown': 'function omit(){}'
  1279. })
  1280. );
  1281. /*--------------------------------------------------------------------------*/
  1282. suites.push(
  1283. Benchmark.Suite('`_.partial` (slow path)')
  1284. .add(buildName, {
  1285. 'fn': 'lodash.partial(function(greeting) { return greeting + " " + this.name; }, "hi")',
  1286. 'teardown': 'function partial(){}'
  1287. })
  1288. .add(otherName, {
  1289. 'fn': '_.partial(function(greeting) { return greeting + " " + this.name; }, "hi")',
  1290. 'teardown': 'function partial(){}'
  1291. })
  1292. );
  1293. suites.push(
  1294. Benchmark.Suite('partially applied call with arguments')
  1295. .add(buildName, {
  1296. 'fn': 'lodashPartial("!")',
  1297. 'teardown': 'function partial(){}'
  1298. })
  1299. .add(otherName, {
  1300. 'fn': '_partial("!")',
  1301. 'teardown': 'function partial(){}'
  1302. })
  1303. );
  1304. /*--------------------------------------------------------------------------*/
  1305. suites.push(
  1306. Benchmark.Suite('`_.partition` iterating an array')
  1307. .add(buildName, '\
  1308. lodash.partition(numbers, function(num) {\
  1309. return num % 2;\
  1310. })'
  1311. )
  1312. .add(otherName, '\
  1313. _.partition(numbers, function(num) {\
  1314. return num % 2;\
  1315. })'
  1316. )
  1317. );
  1318. suites.push(
  1319. Benchmark.Suite('`_.partition` iterating an object')
  1320. .add(buildName, '\
  1321. lodash.partition(object, function(num) {\
  1322. return num % 2;\
  1323. })'
  1324. )
  1325. .add(otherName, '\
  1326. _.partition(object, function(num) {\
  1327. return num % 2;\
  1328. })'
  1329. )
  1330. );
  1331. /*--------------------------------------------------------------------------*/
  1332. suites.push(
  1333. Benchmark.Suite('`_.pick`')
  1334. .add(buildName, '\
  1335. lodash.pick(object, "key6", "key13")'
  1336. )
  1337. .add(otherName, '\
  1338. _.pick(object, "key6", "key13")'
  1339. )
  1340. );
  1341. /*--------------------------------------------------------------------------*/
  1342. suites.push(
  1343. Benchmark.Suite('`_.reduce` iterating an array')
  1344. .add(buildName, '\
  1345. lodash.reduce(numbers, function(result, value, index) {\
  1346. result[index] = value;\
  1347. return result;\
  1348. }, {})'
  1349. )
  1350. .add(otherName, '\
  1351. _.reduce(numbers, function(result, value, index) {\
  1352. result[index] = value;\
  1353. return result;\
  1354. }, {})'
  1355. )
  1356. );
  1357. suites.push(
  1358. Benchmark.Suite('`_.reduce` iterating an object')
  1359. .add(buildName, '\
  1360. lodash.reduce(object, function(result, value, key) {\
  1361. result.push(key, value);\
  1362. return result;\
  1363. }, [])'
  1364. )
  1365. .add(otherName, '\
  1366. _.reduce(object, function(result, value, key) {\
  1367. result.push(key, value);\
  1368. return result;\
  1369. }, [])'
  1370. )
  1371. );
  1372. /*--------------------------------------------------------------------------*/
  1373. suites.push(
  1374. Benchmark.Suite('`_.reduceRight` iterating an array')
  1375. .add(buildName, '\
  1376. lodash.reduceRight(numbers, function(result, value, index) {\
  1377. result[index] = value;\
  1378. return result;\
  1379. }, {})'
  1380. )
  1381. .add(otherName, '\
  1382. _.reduceRight(numbers, function(result, value, index) {\
  1383. result[index] = value;\
  1384. return result;\
  1385. }, {})'
  1386. )
  1387. );
  1388. suites.push(
  1389. Benchmark.Suite('`_.reduceRight` iterating an object')
  1390. .add(buildName, '\
  1391. lodash.reduceRight(object, function(result, value, key) {\
  1392. result.push(key, value);\
  1393. return result;\
  1394. }, [])'
  1395. )
  1396. .add(otherName, '\
  1397. _.reduceRight(object, function(result, value, key) {\
  1398. result.push(key, value);\
  1399. return result;\
  1400. }, [])'
  1401. )
  1402. );
  1403. /*--------------------------------------------------------------------------*/
  1404. suites.push(
  1405. Benchmark.Suite('`_.reject` iterating an array')
  1406. .add(buildName, '\
  1407. lodash.reject(numbers, function(num) {\
  1408. return num % 2;\
  1409. })'
  1410. )
  1411. .add(otherName, '\
  1412. _.reject(numbers, function(num) {\
  1413. return num % 2;\
  1414. })'
  1415. )
  1416. );
  1417. suites.push(
  1418. Benchmark.Suite('`_.reject` iterating an object')
  1419. .add(buildName, '\
  1420. lodash.reject(object, function(num) {\
  1421. return num % 2;\
  1422. })'
  1423. )
  1424. .add(otherName, '\
  1425. _.reject(object, function(num) {\
  1426. return num % 2;\
  1427. })'
  1428. )
  1429. );
  1430. /*--------------------------------------------------------------------------*/
  1431. suites.push(
  1432. Benchmark.Suite('`_.sampleSize`')
  1433. .add(buildName, '\
  1434. lodash.sampleSize(numbers, limit / 2)'
  1435. )
  1436. .add(otherName, '\
  1437. _.sampleSize(numbers, limit / 2)'
  1438. )
  1439. );
  1440. /*--------------------------------------------------------------------------*/
  1441. suites.push(
  1442. Benchmark.Suite('`_.shuffle`')
  1443. .add(buildName, '\
  1444. lodash.shuffle(numbers)'
  1445. )
  1446. .add(otherName, '\
  1447. _.shuffle(numbers)'
  1448. )
  1449. );
  1450. /*--------------------------------------------------------------------------*/
  1451. suites.push(
  1452. Benchmark.Suite('`_.size` with an object')
  1453. .add(buildName, '\
  1454. lodash.size(object)'
  1455. )
  1456. .add(otherName, '\
  1457. _.size(object)'
  1458. )
  1459. );
  1460. /*--------------------------------------------------------------------------*/
  1461. suites.push(
  1462. Benchmark.Suite('`_.some` iterating an array')
  1463. .add(buildName, '\
  1464. lodash.some(numbers, function(num) {\
  1465. return num == (limit - 1);\
  1466. })'
  1467. )
  1468. .add(otherName, '\
  1469. _.some(numbers, function(num) {\
  1470. return num == (limit - 1);\
  1471. })'
  1472. )
  1473. );
  1474. suites.push(
  1475. Benchmark.Suite('`_.some` iterating an object')
  1476. .add(buildName, '\
  1477. lodash.some(object, function(num) {\
  1478. return num == (limit - 1);\
  1479. })'
  1480. )
  1481. .add(otherName, '\
  1482. _.some(object, function(num) {\
  1483. return num == (limit - 1);\
  1484. })'
  1485. )
  1486. );
  1487. /*--------------------------------------------------------------------------*/
  1488. suites.push(
  1489. Benchmark.Suite('`_.sortBy` with `callback`')
  1490. .add(buildName, '\
  1491. lodash.sortBy(numbers, function(num) { return Math.sin(num); })'
  1492. )
  1493. .add(otherName, '\
  1494. _.sortBy(numbers, function(num) { return Math.sin(num); })'
  1495. )
  1496. );
  1497. suites.push(
  1498. Benchmark.Suite('`_.sortBy` with `property` name')
  1499. .add(buildName, {
  1500. 'fn': 'lodash.sortBy(words, "length")',
  1501. 'teardown': 'function countBy(){}'
  1502. })
  1503. .add(otherName, {
  1504. 'fn': '_.sortBy(words, "length")',
  1505. 'teardown': 'function countBy(){}'
  1506. })
  1507. );
  1508. /*--------------------------------------------------------------------------*/
  1509. suites.push(
  1510. Benchmark.Suite('`_.sortedIndex`')
  1511. .add(buildName, '\
  1512. lodash.sortedIndex(numbers, limit)'
  1513. )
  1514. .add(otherName, '\
  1515. _.sortedIndex(numbers, limit)'
  1516. )
  1517. );
  1518. /*--------------------------------------------------------------------------*/
  1519. suites.push(
  1520. Benchmark.Suite('`_.sortedIndexBy`')
  1521. .add(buildName, {
  1522. 'fn': '\
  1523. lodash.sortedIndexBy(words, "twenty-five", function(value) {\
  1524. return wordToNumber[value];\
  1525. })',
  1526. 'teardown': 'function countBy(){}'
  1527. })
  1528. .add(otherName, {
  1529. 'fn': '\
  1530. _.sortedIndexBy(words, "twenty-five", function(value) {\
  1531. return wordToNumber[value];\
  1532. })',
  1533. 'teardown': 'function countBy(){}'
  1534. })
  1535. );
  1536. /*--------------------------------------------------------------------------*/
  1537. suites.push(
  1538. Benchmark.Suite('`_.sortedIndexOf`')
  1539. .add(buildName, {
  1540. 'fn': 'lodash.sortedIndexOf(hundredSortedValues, 99)',
  1541. 'teardown': 'function multiArrays(){}'
  1542. })
  1543. .add(otherName, {
  1544. 'fn': '_.sortedIndexOf(hundredSortedValues, 99)',
  1545. 'teardown': 'function multiArrays(){}'
  1546. })
  1547. );
  1548. /*--------------------------------------------------------------------------*/
  1549. suites.push(
  1550. Benchmark.Suite('`_.sortedLastIndexOf`')
  1551. .add(buildName, {
  1552. 'fn': 'lodash.sortedLastIndexOf(hundredSortedValues, 0)',
  1553. 'teardown': 'function multiArrays(){}'
  1554. })
  1555. .add(otherName, {
  1556. 'fn': '_.sortedLastIndexOf(hundredSortedValues, 0)',
  1557. 'teardown': 'function multiArrays(){}'
  1558. })
  1559. );
  1560. /*--------------------------------------------------------------------------*/
  1561. suites.push(
  1562. Benchmark.Suite('`_.sum`')
  1563. .add(buildName, '\
  1564. lodash.sum(numbers)'
  1565. )
  1566. .add(otherName, '\
  1567. _.sum(numbers)'
  1568. )
  1569. );
  1570. /*--------------------------------------------------------------------------*/
  1571. suites.push(
  1572. Benchmark.Suite('`_.template` (slow path)')
  1573. .add(buildName, {
  1574. 'fn': 'lodash.template(tpl)(tplData)',
  1575. 'teardown': 'function template(){}'
  1576. })
  1577. .add(otherName, {
  1578. 'fn': '_.template(tpl)(tplData)',
  1579. 'teardown': 'function template(){}'
  1580. })
  1581. );
  1582. suites.push(
  1583. Benchmark.Suite('compiled template')
  1584. .add(buildName, {
  1585. 'fn': 'lodashTpl(tplData)',
  1586. 'teardown': 'function template(){}'
  1587. })
  1588. .add(otherName, {
  1589. 'fn': '_tpl(tplData)',
  1590. 'teardown': 'function template(){}'
  1591. })
  1592. );
  1593. suites.push(
  1594. Benchmark.Suite('compiled template without a with-statement')
  1595. .add(buildName, {
  1596. 'fn': 'lodashTplVerbose(tplData)',
  1597. 'teardown': 'function template(){}'
  1598. })
  1599. .add(otherName, {
  1600. 'fn': '_tplVerbose(tplData)',
  1601. 'teardown': 'function template(){}'
  1602. })
  1603. );
  1604. /*--------------------------------------------------------------------------*/
  1605. suites.push(
  1606. Benchmark.Suite('`_.times`')
  1607. .add(buildName, '\
  1608. var result = [];\
  1609. lodash.times(limit, function(n) { result.push(n); })'
  1610. )
  1611. .add(otherName, '\
  1612. var result = [];\
  1613. _.times(limit, function(n) { result.push(n); })'
  1614. )
  1615. );
  1616. /*--------------------------------------------------------------------------*/
  1617. suites.push(
  1618. Benchmark.Suite('`_.toArray` with an array (edge case)')
  1619. .add(buildName, '\
  1620. lodash.toArray(numbers)'
  1621. )
  1622. .add(otherName, '\
  1623. _.toArray(numbers)'
  1624. )
  1625. );
  1626. suites.push(
  1627. Benchmark.Suite('`_.toArray` with an object')
  1628. .add(buildName, '\
  1629. lodash.toArray(object)'
  1630. )
  1631. .add(otherName, '\
  1632. _.toArray(object)'
  1633. )
  1634. );
  1635. /*--------------------------------------------------------------------------*/
  1636. suites.push(
  1637. Benchmark.Suite('`_.toPairs`')
  1638. .add(buildName, '\
  1639. lodash.toPairs(object)'
  1640. )
  1641. .add(otherName, '\
  1642. _.toPairs(object)'
  1643. )
  1644. );
  1645. /*--------------------------------------------------------------------------*/
  1646. suites.push(
  1647. Benchmark.Suite('`_.unescape` string without html entities')
  1648. .add(buildName, '\
  1649. lodash.unescape("`&`, `<`, `>`, `\\"`, and `\'`")'
  1650. )
  1651. .add(otherName, '\
  1652. _.unescape("`&`, `<`, `>`, `\\"`, and `\'`")'
  1653. )
  1654. );
  1655. suites.push(
  1656. Benchmark.Suite('`_.unescape` string with html entities')
  1657. .add(buildName, '\
  1658. lodash.unescape("`&amp;`, `&lt;`, `&gt;`, `&quot;`, and `&#39;`")'
  1659. )
  1660. .add(otherName, '\
  1661. _.unescape("`&amp;`, `&lt;`, `&gt;`, `&quot;`, and `&#39;`")'
  1662. )
  1663. );
  1664. /*--------------------------------------------------------------------------*/
  1665. suites.push(
  1666. Benchmark.Suite('`_.union`')
  1667. .add(buildName, '\
  1668. lodash.union(numbers, twoNumbers, fourNumbers)'
  1669. )
  1670. .add(otherName, '\
  1671. _.union(numbers, twoNumbers, fourNumbers)'
  1672. )
  1673. );
  1674. suites.push(
  1675. Benchmark.Suite('`_.union` iterating an array of 200 elements')
  1676. .add(buildName, {
  1677. 'fn': 'lodash.union(hundredValues, hundredValues2)',
  1678. 'teardown': 'function multiArrays(){}'
  1679. })
  1680. .add(otherName, {
  1681. 'fn': '_.union(hundredValues, hundredValues2)',
  1682. 'teardown': 'function multiArrays(){}'
  1683. })
  1684. );
  1685. /*--------------------------------------------------------------------------*/
  1686. suites.push(
  1687. Benchmark.Suite('`_.uniq`')
  1688. .add(buildName, '\
  1689. lodash.uniq(numbers.concat(twoNumbers, fourNumbers))'
  1690. )
  1691. .add(otherName, '\
  1692. _.uniq(numbers.concat(twoNumbers, fourNumbers))'
  1693. )
  1694. );
  1695. suites.push(
  1696. Benchmark.Suite('`_.uniq` iterating an array of 200 elements')
  1697. .add(buildName, {
  1698. 'fn': 'lodash.uniq(twoHundredValues)',
  1699. 'teardown': 'function multiArrays(){}'
  1700. })
  1701. .add(otherName, {
  1702. 'fn': '_.uniq(twoHundredValues)',
  1703. 'teardown': 'function multiArrays(){}'
  1704. })
  1705. );
  1706. /*--------------------------------------------------------------------------*/
  1707. suites.push(
  1708. Benchmark.Suite('`_.uniqBy`')
  1709. .add(buildName, '\
  1710. lodash.uniqBy(numbers.concat(twoNumbers, fourNumbers), function(num) {\
  1711. return num % 2;\
  1712. })'
  1713. )
  1714. .add(otherName, '\
  1715. _.uniqBy(numbers.concat(twoNumbers, fourNumbers), function(num) {\
  1716. return num % 2;\
  1717. })'
  1718. )
  1719. );
  1720. /*--------------------------------------------------------------------------*/
  1721. suites.push(
  1722. Benchmark.Suite('`_.values`')
  1723. .add(buildName, '\
  1724. lodash.values(object)'
  1725. )
  1726. .add(otherName, '\
  1727. _.values(object)'
  1728. )
  1729. );
  1730. /*--------------------------------------------------------------------------*/
  1731. suites.push(
  1732. Benchmark.Suite('`_.without`')
  1733. .add(buildName, '\
  1734. lodash.without(numbers, 9, 12, 14, 15)'
  1735. )
  1736. .add(otherName, '\
  1737. _.without(numbers, 9, 12, 14, 15)'
  1738. )
  1739. );
  1740. /*--------------------------------------------------------------------------*/
  1741. suites.push(
  1742. Benchmark.Suite('`_.wrap` result called')
  1743. .add(buildName, {
  1744. 'fn': 'lodashWrapped(2, 5)',
  1745. 'teardown': 'function wrap(){}'
  1746. })
  1747. .add(otherName, {
  1748. 'fn': '_wrapped(2, 5)',
  1749. 'teardown': 'function wrap(){}'
  1750. })
  1751. );
  1752. /*--------------------------------------------------------------------------*/
  1753. suites.push(
  1754. Benchmark.Suite('`_.zip`')
  1755. .add(buildName, {
  1756. 'fn': 'lodash.zip.apply(lodash, unzipped)',
  1757. 'teardown': 'function zip(){}'
  1758. })
  1759. .add(otherName, {
  1760. 'fn': '_.zip.apply(_, unzipped)',
  1761. 'teardown': 'function zip(){}'
  1762. })
  1763. );
  1764. /*--------------------------------------------------------------------------*/
  1765. if (Benchmark.platform + '') {
  1766. log(Benchmark.platform);
  1767. }
  1768. // Expose `run` to be called later when executing in a browser.
  1769. if (document) {
  1770. root.run = run;
  1771. } else {
  1772. run();
  1773. }
  1774. }.call(this));