mirror of
https://github.com/whoisclebs/lodash.git
synced 2026-02-08 10:17:48 +00:00
Reduce temporary objects created in _.merge, _.clone, and _.isEqual.
Former-commit-id: e6696642505f39eefdf59075ff8a993ab033465a
This commit is contained in:
@@ -44,7 +44,7 @@
|
|||||||
'callee',
|
'callee',
|
||||||
'className',
|
'className',
|
||||||
'compareAscending',
|
'compareAscending',
|
||||||
'destValue',
|
'data',
|
||||||
'forIn',
|
'forIn',
|
||||||
'found',
|
'found',
|
||||||
'funcs',
|
'funcs',
|
||||||
@@ -66,10 +66,11 @@
|
|||||||
'propsLength',
|
'propsLength',
|
||||||
'recursive',
|
'recursive',
|
||||||
'source',
|
'source',
|
||||||
'stack',
|
'sources',
|
||||||
'stackLength',
|
'stackLength',
|
||||||
'target',
|
'target',
|
||||||
'valueProp'
|
'valueProp',
|
||||||
|
'values'
|
||||||
];
|
];
|
||||||
|
|
||||||
/** Used to minify `compileIterator` option properties */
|
/** Used to minify `compileIterator` option properties */
|
||||||
@@ -107,18 +108,17 @@
|
|||||||
'__chain__',
|
'__chain__',
|
||||||
'__proto__',
|
'__proto__',
|
||||||
'__wrapped__',
|
'__wrapped__',
|
||||||
'a',
|
|
||||||
'after',
|
'after',
|
||||||
'all',
|
'all',
|
||||||
'amd',
|
'amd',
|
||||||
'any',
|
'any',
|
||||||
'attachEvent',
|
'attachEvent',
|
||||||
'b',
|
|
||||||
'bind',
|
'bind',
|
||||||
'bindAll',
|
'bindAll',
|
||||||
'chain',
|
'chain',
|
||||||
'clearTimeout',
|
'clearTimeout',
|
||||||
'clone',
|
'clone',
|
||||||
|
'clones',
|
||||||
'collect',
|
'collect',
|
||||||
'compact',
|
'compact',
|
||||||
'compose',
|
'compose',
|
||||||
@@ -214,6 +214,9 @@
|
|||||||
'sortBy',
|
'sortBy',
|
||||||
'sortedIndex',
|
'sortedIndex',
|
||||||
'source',
|
'source',
|
||||||
|
'sources',
|
||||||
|
'stackA',
|
||||||
|
'stackB',
|
||||||
'tail',
|
'tail',
|
||||||
'take',
|
'take',
|
||||||
'tap',
|
'tap',
|
||||||
@@ -304,7 +307,7 @@
|
|||||||
|
|
||||||
// minify internal properties used by 'compareAscending', `_.clone`, `_.isEqual`, `_.merge`, and `_.sortBy`
|
// minify internal properties used by 'compareAscending', `_.clone`, `_.isEqual`, `_.merge`, and `_.sortBy`
|
||||||
(function() {
|
(function() {
|
||||||
var properties = ['criteria', 'index', 'source', 'thorough', 'value'],
|
var properties = ['clones', 'criteria', 'index', 'sources', 'thorough', 'value', 'values'],
|
||||||
snippets = source.match(/( +)(?:function (?:clone|compareAscending|isEqual)|var merge|var sortBy)\b[\s\S]+?\n\1}/g);
|
snippets = source.match(/( +)(?:function (?:clone|compareAscending|isEqual)|var merge|var sortBy)\b[\s\S]+?\n\1}/g);
|
||||||
|
|
||||||
if (!snippets) {
|
if (!snippets) {
|
||||||
@@ -319,7 +322,7 @@
|
|||||||
properties.forEach(function(property, index) {
|
properties.forEach(function(property, index) {
|
||||||
var reBracketProp = RegExp("\\['(" + property + ")'\\]", 'g'),
|
var reBracketProp = RegExp("\\['(" + property + ")'\\]", 'g'),
|
||||||
reDotProp = RegExp('\\.' + property + '\\b', 'g'),
|
reDotProp = RegExp('\\.' + property + '\\b', 'g'),
|
||||||
rePropColon = RegExp("(')?\\b" + property + "\\1 *:", 'g');
|
rePropColon = RegExp("([^?])(')?\\b" + property + "\\2 *:", 'g');
|
||||||
|
|
||||||
if (isCompilable) {
|
if (isCompilable) {
|
||||||
// add quotes around properties in the inlined `_.merge` and `_.sortBy`
|
// add quotes around properties in the inlined `_.merge` and `_.sortBy`
|
||||||
@@ -328,20 +331,20 @@
|
|||||||
modified = modified
|
modified = modified
|
||||||
.replace(reBracketProp, "['" + minNames[index] + "']")
|
.replace(reBracketProp, "['" + minNames[index] + "']")
|
||||||
.replace(reDotProp, "['" + minNames[index] + "']")
|
.replace(reDotProp, "['" + minNames[index] + "']")
|
||||||
.replace(rePropColon, "'" + minNames[index] + "':");
|
.replace(rePropColon, "$1'" + minNames[index] + "':");
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
modified = modified
|
modified = modified
|
||||||
.replace(reBracketProp, '.' + minNames[index])
|
.replace(reBracketProp, '.' + minNames[index])
|
||||||
.replace(reDotProp, '.' + minNames[index])
|
.replace(reDotProp, '.' + minNames[index])
|
||||||
.replace(rePropColon, minNames[index] + ':');
|
.replace(rePropColon, '$1' + minNames[index] + ':');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
modified = modified
|
modified = modified
|
||||||
.replace(reBracketProp, "['" + minNames[index] + "']")
|
.replace(reBracketProp, "['" + minNames[index] + "']")
|
||||||
.replace(reDotProp, '.' + minNames[index])
|
.replace(reDotProp, '.' + minNames[index])
|
||||||
.replace(rePropColon, "'" + minNames[index] + "':")
|
.replace(rePropColon, "$1'" + minNames[index] + "':")
|
||||||
|
|
||||||
// correct `value.source` in regexp branch of `_.clone`
|
// correct `value.source` in regexp branch of `_.clone`
|
||||||
if (property == 'source') {
|
if (property == 'source') {
|
||||||
|
|||||||
52
lodash.js
52
lodash.js
@@ -1141,13 +1141,14 @@
|
|||||||
return ctor(value.source, reFlags.exec(value));
|
return ctor(value.source, reFlags.exec(value));
|
||||||
}
|
}
|
||||||
|
|
||||||
var stack = data.stack || (data.stack = []),
|
var clones = data.clones || (data.clones = []),
|
||||||
length = stack.length;
|
sources = data.sources || (data.sources = []),
|
||||||
|
length = clones.length;
|
||||||
|
|
||||||
// check for circular references and return corresponding clone
|
// check for circular references and return corresponding clone
|
||||||
while (length--) {
|
while (length--) {
|
||||||
if (stack[length].source == value) {
|
if (sources[length] == value) {
|
||||||
return stack[length].value;
|
return clones[length];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1155,7 +1156,8 @@
|
|||||||
var result = isArr ? ctor(length = value.length) : {};
|
var result = isArr ? ctor(length = value.length) : {};
|
||||||
|
|
||||||
// add current clone and original source value to the stack of traversed objects
|
// add current clone and original source value to the stack of traversed objects
|
||||||
stack.push({ 'value': result, 'source': value });
|
clones.push(result);
|
||||||
|
sources.push(value);
|
||||||
|
|
||||||
// recursively populate clone (susceptible to call stack limits)
|
// recursively populate clone (susceptible to call stack limits)
|
||||||
if (isArr) {
|
if (isArr) {
|
||||||
@@ -1512,12 +1514,13 @@
|
|||||||
// assume cyclic structures are equal
|
// assume cyclic structures are equal
|
||||||
// the algorithm for detecting cyclic structures is adapted from ES 5.1
|
// the algorithm for detecting cyclic structures is adapted from ES 5.1
|
||||||
// section 15.12.3, abstract operation `JO` (http://es5.github.com/#x15.12.3)
|
// section 15.12.3, abstract operation `JO` (http://es5.github.com/#x15.12.3)
|
||||||
var stack = data.stack || (data.stack = []),
|
var stackA = data.stackA || (data.stackA = []),
|
||||||
length = stack.length;
|
stackB = data.stackB || (data.stackB = []),
|
||||||
|
length = stackA.length;
|
||||||
|
|
||||||
while (length--) {
|
while (length--) {
|
||||||
if (stack[length].a == a) {
|
if (stackA[length] == a) {
|
||||||
return stack[length].b == b;
|
return stackA[length] == b;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1526,7 +1529,8 @@
|
|||||||
size = 0;
|
size = 0;
|
||||||
|
|
||||||
// add `a` and `b` to the stack of traversed objects
|
// add `a` and `b` to the stack of traversed objects
|
||||||
stack.push({ 'a': a, 'b': b });
|
stackA.push(a);
|
||||||
|
stackB.push(b);
|
||||||
|
|
||||||
// recursively compare objects and arrays (susceptible to call stack limits)
|
// recursively compare objects and arrays (susceptible to call stack limits)
|
||||||
if (isArr) {
|
if (isArr) {
|
||||||
@@ -1800,7 +1804,7 @@
|
|||||||
* @param {Object} [source1, source2, ...] The source objects.
|
* @param {Object} [source1, source2, ...] The source objects.
|
||||||
* @param {Object} [indicator] Internally used to indicate that the `stack`
|
* @param {Object} [indicator] Internally used to indicate that the `stack`
|
||||||
* argument is an array of traversed objects instead of another source object.
|
* argument is an array of traversed objects instead of another source object.
|
||||||
* @param {Array} [stack=[]] Internally used to track traversed objects to avoid
|
* @param {Object} [data={}] Internally used to track traversed objects to avoid
|
||||||
* circular references.
|
* circular references.
|
||||||
* @returns {Object} Returns the destination object.
|
* @returns {Object} Returns the destination object.
|
||||||
* @example
|
* @example
|
||||||
@@ -1821,26 +1825,28 @@
|
|||||||
var merge = createIterator(extendIteratorOptions, {
|
var merge = createIterator(extendIteratorOptions, {
|
||||||
'args': 'object, source, indicator',
|
'args': 'object, source, indicator',
|
||||||
'top':
|
'top':
|
||||||
'var isArr, recursive = indicator == isPlainObject, stack = recursive ? arguments[3] : [];\n' +
|
'var isArr, source, recursive = indicator == isPlainObject,\n' +
|
||||||
|
' data = recursive ? arguments[3] : { values: [], sources: [] };\n' +
|
||||||
'for (var argsIndex = 1, argsLength = recursive ? 2 : arguments.length; argsIndex < argsLength; argsIndex++) {\n' +
|
'for (var argsIndex = 1, argsLength = recursive ? 2 : arguments.length; argsIndex < argsLength; argsIndex++) {\n' +
|
||||||
' if (iteratee = arguments[argsIndex]) {',
|
' if (iteratee = arguments[argsIndex]) {',
|
||||||
'inLoop':
|
'inLoop':
|
||||||
'if (value && ((isArr = isArray(value)) || isPlainObject(value))) {\n' +
|
'if ((source = value) && ((isArr = isArray(source)) || isPlainObject(source))) {\n' +
|
||||||
' var found = false, stackLength = stack.length;\n' +
|
' var found = false, values = data.values, sources = data.sources, stackLength = sources.length;\n' +
|
||||||
' while (stackLength--) {\n' +
|
' while (stackLength--) {\n' +
|
||||||
' if (found = stack[stackLength].source == value) break\n' +
|
' if (found = sources[stackLength] == source) break\n' +
|
||||||
' }\n' +
|
' }\n' +
|
||||||
' if (found) {\n' +
|
' if (found) {\n' +
|
||||||
' result[index] = stack[stackLength].value\n' +
|
' result[index] = values[stackLength]\n' +
|
||||||
' } else {\n' +
|
' } else {\n' +
|
||||||
' var destValue = (destValue = result[index]) && isArr\n' +
|
' sources.push(source);\n' +
|
||||||
' ? (isArray(destValue) ? destValue : [])\n' +
|
' values.push(value = (value = result[index]) && isArr\n' +
|
||||||
' : (isPlainObject(destValue) ? destValue : {});\n' +
|
' ? (isArray(value) ? value : [])\n' +
|
||||||
' stack.push({ value: destValue, source: value });\n' +
|
' : (isPlainObject(value) ? value : {})\n' +
|
||||||
' result[index] = callee(destValue, value, isPlainObject, stack)\n' +
|
' );\n' +
|
||||||
|
' result[index] = callee(value, source, isPlainObject, data)\n' +
|
||||||
' }\n' +
|
' }\n' +
|
||||||
'} else if (value != null) {\n' +
|
'} else if (source != null) {\n' +
|
||||||
' result[index] = value\n' +
|
' result[index] = source\n' +
|
||||||
'}'
|
'}'
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user