mirror of
https://github.com/whoisclebs/lodash.git
synced 2026-02-01 23:57:49 +00:00
Add baseRest.
This commit is contained in:
153
lodash.js
153
lodash.js
@@ -3664,6 +3664,40 @@
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* The base implementation of `_.rest` which doesn't validate or coerce arguments.
|
||||
*
|
||||
* @private
|
||||
* @param {Function} func The function to apply a rest parameter to.
|
||||
* @param {number} [start=func.length-1] The start position of the rest parameter.
|
||||
* @returns {Function} Returns the new function.
|
||||
*/
|
||||
function baseRest(func, start) {
|
||||
start = nativeMax(start === undefined ? (func.length - 1) : start, 0);
|
||||
return function() {
|
||||
var args = arguments,
|
||||
index = -1,
|
||||
length = nativeMax(args.length - start, 0),
|
||||
array = Array(length);
|
||||
|
||||
while (++index < length) {
|
||||
array[index] = args[start + index];
|
||||
}
|
||||
switch (start) {
|
||||
case 0: return func.call(this, array);
|
||||
case 1: return func.call(this, args[0], array);
|
||||
case 2: return func.call(this, args[0], args[1], array);
|
||||
}
|
||||
var otherArgs = Array(start + 1);
|
||||
index = -1;
|
||||
while (++index < start) {
|
||||
otherArgs[index] = args[index];
|
||||
}
|
||||
otherArgs[start] = array;
|
||||
return apply(func, this, otherArgs);
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* The base implementation of `_.set`.
|
||||
*
|
||||
@@ -4487,7 +4521,7 @@
|
||||
* @returns {Function} Returns the new assigner function.
|
||||
*/
|
||||
function createAssigner(assigner) {
|
||||
return rest(function(object, sources) {
|
||||
return baseRest(function(object, sources) {
|
||||
var index = -1,
|
||||
length = sources.length,
|
||||
customizer = length > 1 ? sources[length - 1] : undefined,
|
||||
@@ -4724,7 +4758,7 @@
|
||||
* @returns {Function} Returns the new flow function.
|
||||
*/
|
||||
function createFlow(fromRight) {
|
||||
return rest(function(funcs) {
|
||||
return baseRest(function(funcs) {
|
||||
funcs = baseFlatten(funcs, 1);
|
||||
|
||||
var length = funcs.length,
|
||||
@@ -4909,12 +4943,12 @@
|
||||
* @returns {Function} Returns the new over function.
|
||||
*/
|
||||
function createOver(arrayFunc) {
|
||||
return rest(function(iteratees) {
|
||||
return baseRest(function(iteratees) {
|
||||
iteratees = (iteratees.length == 1 && isArray(iteratees[0]))
|
||||
? arrayMap(iteratees[0], baseUnary(getIteratee()))
|
||||
: arrayMap(baseFlatten(iteratees, 1), baseUnary(getIteratee()));
|
||||
|
||||
return rest(function(args) {
|
||||
return baseRest(function(args) {
|
||||
var thisArg = this;
|
||||
return arrayFunc(iteratees, function(iteratee) {
|
||||
return apply(iteratee, thisArg, args);
|
||||
@@ -6406,7 +6440,7 @@
|
||||
* _.difference([2, 1], [2, 3]);
|
||||
* // => [1]
|
||||
*/
|
||||
var difference = rest(function(array, values) {
|
||||
var difference = baseRest(function(array, values) {
|
||||
return isArrayLikeObject(array)
|
||||
? baseDifference(array, baseFlatten(values, 1, isArrayLikeObject, true))
|
||||
: [];
|
||||
@@ -6437,7 +6471,7 @@
|
||||
* _.differenceBy([{ 'x': 2 }, { 'x': 1 }], [{ 'x': 1 }], 'x');
|
||||
* // => [{ 'x': 2 }]
|
||||
*/
|
||||
var differenceBy = rest(function(array, values) {
|
||||
var differenceBy = baseRest(function(array, values) {
|
||||
var iteratee = last(values);
|
||||
if (isArrayLikeObject(iteratee)) {
|
||||
iteratee = undefined;
|
||||
@@ -6470,7 +6504,7 @@
|
||||
* _.differenceWith(objects, [{ 'x': 1, 'y': 2 }], _.isEqual);
|
||||
* // => [{ 'x': 2, 'y': 1 }]
|
||||
*/
|
||||
var differenceWith = rest(function(array, values) {
|
||||
var differenceWith = baseRest(function(array, values) {
|
||||
var comparator = last(values);
|
||||
if (isArrayLikeObject(comparator)) {
|
||||
comparator = undefined;
|
||||
@@ -6958,7 +6992,7 @@
|
||||
* _.intersection([2, 1], [2, 3]);
|
||||
* // => [2]
|
||||
*/
|
||||
var intersection = rest(function(arrays) {
|
||||
var intersection = baseRest(function(arrays) {
|
||||
var mapped = arrayMap(arrays, castArrayLikeObject);
|
||||
return (mapped.length && mapped[0] === arrays[0])
|
||||
? baseIntersection(mapped)
|
||||
@@ -6987,7 +7021,7 @@
|
||||
* _.intersectionBy([{ 'x': 1 }], [{ 'x': 2 }, { 'x': 1 }], 'x');
|
||||
* // => [{ 'x': 1 }]
|
||||
*/
|
||||
var intersectionBy = rest(function(arrays) {
|
||||
var intersectionBy = baseRest(function(arrays) {
|
||||
var iteratee = last(arrays),
|
||||
mapped = arrayMap(arrays, castArrayLikeObject);
|
||||
|
||||
@@ -7022,7 +7056,7 @@
|
||||
* _.intersectionWith(objects, others, _.isEqual);
|
||||
* // => [{ 'x': 1, 'y': 2 }]
|
||||
*/
|
||||
var intersectionWith = rest(function(arrays) {
|
||||
var intersectionWith = baseRest(function(arrays) {
|
||||
var comparator = last(arrays),
|
||||
mapped = arrayMap(arrays, castArrayLikeObject);
|
||||
|
||||
@@ -7168,7 +7202,7 @@
|
||||
* console.log(array);
|
||||
* // => ['b', 'b']
|
||||
*/
|
||||
var pull = rest(pullAll);
|
||||
var pull = baseRest(pullAll);
|
||||
|
||||
/**
|
||||
* This method is like `_.pull` except that it accepts an array of values to remove.
|
||||
@@ -7279,7 +7313,7 @@
|
||||
* console.log(pulled);
|
||||
* // => ['b', 'd']
|
||||
*/
|
||||
var pullAt = rest(function(array, indexes) {
|
||||
var pullAt = baseRest(function(array, indexes) {
|
||||
indexes = baseFlatten(indexes, 1);
|
||||
|
||||
var length = array ? array.length : 0,
|
||||
@@ -7787,7 +7821,7 @@
|
||||
* _.union([2], [1, 2]);
|
||||
* // => [2, 1]
|
||||
*/
|
||||
var union = rest(function(arrays) {
|
||||
var union = baseRest(function(arrays) {
|
||||
return baseUniq(baseFlatten(arrays, 1, isArrayLikeObject, true));
|
||||
});
|
||||
|
||||
@@ -7815,7 +7849,7 @@
|
||||
* _.unionBy([{ 'x': 1 }], [{ 'x': 2 }, { 'x': 1 }], 'x');
|
||||
* // => [{ 'x': 1 }, { 'x': 2 }]
|
||||
*/
|
||||
var unionBy = rest(function(arrays) {
|
||||
var unionBy = baseRest(function(arrays) {
|
||||
var iteratee = last(arrays);
|
||||
if (isArrayLikeObject(iteratee)) {
|
||||
iteratee = undefined;
|
||||
@@ -7844,7 +7878,7 @@
|
||||
* _.unionWith(objects, others, _.isEqual);
|
||||
* // => [{ 'x': 1, 'y': 2 }, { 'x': 2, 'y': 1 }, { 'x': 1, 'y': 1 }]
|
||||
*/
|
||||
var unionWith = rest(function(arrays) {
|
||||
var unionWith = baseRest(function(arrays) {
|
||||
var comparator = last(arrays);
|
||||
if (isArrayLikeObject(comparator)) {
|
||||
comparator = undefined;
|
||||
@@ -8017,7 +8051,7 @@
|
||||
* _.without([2, 1, 2, 3], 1, 2);
|
||||
* // => [3]
|
||||
*/
|
||||
var without = rest(function(array, values) {
|
||||
var without = baseRest(function(array, values) {
|
||||
return isArrayLikeObject(array)
|
||||
? baseDifference(array, values)
|
||||
: [];
|
||||
@@ -8041,7 +8075,7 @@
|
||||
* _.xor([2, 1], [2, 3]);
|
||||
* // => [1, 3]
|
||||
*/
|
||||
var xor = rest(function(arrays) {
|
||||
var xor = baseRest(function(arrays) {
|
||||
return baseXor(arrayFilter(arrays, isArrayLikeObject));
|
||||
});
|
||||
|
||||
@@ -8068,7 +8102,7 @@
|
||||
* _.xorBy([{ 'x': 1 }], [{ 'x': 2 }, { 'x': 1 }], 'x');
|
||||
* // => [{ 'x': 2 }]
|
||||
*/
|
||||
var xorBy = rest(function(arrays) {
|
||||
var xorBy = baseRest(function(arrays) {
|
||||
var iteratee = last(arrays);
|
||||
if (isArrayLikeObject(iteratee)) {
|
||||
iteratee = undefined;
|
||||
@@ -8096,7 +8130,7 @@
|
||||
* _.xorWith(objects, others, _.isEqual);
|
||||
* // => [{ 'x': 2, 'y': 1 }, { 'x': 1, 'y': 1 }]
|
||||
*/
|
||||
var xorWith = rest(function(arrays) {
|
||||
var xorWith = baseRest(function(arrays) {
|
||||
var comparator = last(arrays);
|
||||
if (isArrayLikeObject(comparator)) {
|
||||
comparator = undefined;
|
||||
@@ -8120,7 +8154,7 @@
|
||||
* _.zip(['a', 'b'], [1, 2], [true, false]);
|
||||
* // => [['a', 1, true], ['b', 2, false]]
|
||||
*/
|
||||
var zip = rest(unzip);
|
||||
var zip = baseRest(unzip);
|
||||
|
||||
/**
|
||||
* This method is like `_.fromPairs` except that it accepts two arrays,
|
||||
@@ -8180,7 +8214,7 @@
|
||||
* });
|
||||
* // => [111, 222]
|
||||
*/
|
||||
var zipWith = rest(function(arrays) {
|
||||
var zipWith = baseRest(function(arrays) {
|
||||
var length = arrays.length,
|
||||
iteratee = length > 1 ? arrays[length - 1] : undefined;
|
||||
|
||||
@@ -8296,7 +8330,7 @@
|
||||
* _(object).at(['a[0].b.c', 'a[1]']).value();
|
||||
* // => [3, 4]
|
||||
*/
|
||||
var wrapperAt = rest(function(paths) {
|
||||
var wrapperAt = baseRest(function(paths) {
|
||||
paths = baseFlatten(paths, 1);
|
||||
var length = paths.length,
|
||||
start = length ? paths[0] : 0,
|
||||
@@ -8950,7 +8984,7 @@
|
||||
* _.invokeMap([123, 456], String.prototype.split, '');
|
||||
* // => [['1', '2', '3'], ['4', '5', '6']]
|
||||
*/
|
||||
var invokeMap = rest(function(collection, path, args) {
|
||||
var invokeMap = baseRest(function(collection, path, args) {
|
||||
var index = -1,
|
||||
isFunc = typeof path == 'function',
|
||||
isProp = isKey(path),
|
||||
@@ -9439,7 +9473,7 @@
|
||||
* });
|
||||
* // => objects for [['barney', 36], ['barney', 34], ['fred', 48], ['fred', 40]]
|
||||
*/
|
||||
var sortBy = rest(function(collection, iteratees) {
|
||||
var sortBy = baseRest(function(collection, iteratees) {
|
||||
if (collection == null) {
|
||||
return [];
|
||||
}
|
||||
@@ -9604,7 +9638,7 @@
|
||||
* bound('hi');
|
||||
* // => 'hi fred!'
|
||||
*/
|
||||
var bind = rest(function(func, thisArg, partials) {
|
||||
var bind = baseRest(function(func, thisArg, partials) {
|
||||
var bitmask = BIND_FLAG;
|
||||
if (partials.length) {
|
||||
var holders = replaceHolders(partials, getHolder(bind));
|
||||
@@ -9658,7 +9692,7 @@
|
||||
* bound('hi');
|
||||
* // => 'hiya fred!'
|
||||
*/
|
||||
var bindKey = rest(function(object, key, partials) {
|
||||
var bindKey = baseRest(function(object, key, partials) {
|
||||
var bitmask = BIND_FLAG | BIND_KEY_FLAG;
|
||||
if (partials.length) {
|
||||
var holders = replaceHolders(partials, getHolder(bindKey));
|
||||
@@ -9950,7 +9984,7 @@
|
||||
* }, 'deferred');
|
||||
* // => Logs 'deferred' after one or more milliseconds.
|
||||
*/
|
||||
var defer = rest(function(func, args) {
|
||||
var defer = baseRest(function(func, args) {
|
||||
return baseDelay(func, 1, args);
|
||||
});
|
||||
|
||||
@@ -9973,7 +10007,7 @@
|
||||
* }, 1000, 'later');
|
||||
* // => Logs 'later' after one second.
|
||||
*/
|
||||
var delay = rest(function(func, wait, args) {
|
||||
var delay = baseRest(function(func, wait, args) {
|
||||
return baseDelay(func, toNumber(wait) || 0, args);
|
||||
});
|
||||
|
||||
@@ -10148,13 +10182,13 @@
|
||||
* func(10, 5);
|
||||
* // => [100, 10]
|
||||
*/
|
||||
var overArgs = rest(function(func, transforms) {
|
||||
var overArgs = baseRest(function(func, transforms) {
|
||||
transforms = (transforms.length == 1 && isArray(transforms[0]))
|
||||
? arrayMap(transforms[0], baseUnary(getIteratee()))
|
||||
: arrayMap(baseFlatten(transforms, 1), baseUnary(getIteratee()));
|
||||
|
||||
var funcsLength = transforms.length;
|
||||
return rest(function(args) {
|
||||
return baseRest(function(args) {
|
||||
var index = -1,
|
||||
length = nativeMin(args.length, funcsLength);
|
||||
|
||||
@@ -10198,7 +10232,7 @@
|
||||
* greetFred('hi');
|
||||
* // => 'hi fred'
|
||||
*/
|
||||
var partial = rest(function(func, partials) {
|
||||
var partial = baseRest(function(func, partials) {
|
||||
var holders = replaceHolders(partials, getHolder(partial));
|
||||
return createWrap(func, PARTIAL_FLAG, undefined, partials, holders);
|
||||
});
|
||||
@@ -10235,7 +10269,7 @@
|
||||
* sayHelloTo('fred');
|
||||
* // => 'hello fred'
|
||||
*/
|
||||
var partialRight = rest(function(func, partials) {
|
||||
var partialRight = baseRest(function(func, partials) {
|
||||
var holders = replaceHolders(partials, getHolder(partialRight));
|
||||
return createWrap(func, PARTIAL_RIGHT_FLAG, undefined, partials, holders);
|
||||
});
|
||||
@@ -10262,7 +10296,7 @@
|
||||
* rearged('b', 'c', 'a')
|
||||
* // => ['a', 'b', 'c']
|
||||
*/
|
||||
var rearg = rest(function(func, indexes) {
|
||||
var rearg = baseRest(function(func, indexes) {
|
||||
return createWrap(func, REARG_FLAG, undefined, undefined, undefined, baseFlatten(indexes, 1));
|
||||
});
|
||||
|
||||
@@ -10295,29 +10329,8 @@
|
||||
if (typeof func != 'function') {
|
||||
throw new TypeError(FUNC_ERROR_TEXT);
|
||||
}
|
||||
start = nativeMax(start === undefined ? (func.length - 1) : toInteger(start), 0);
|
||||
return function() {
|
||||
var args = arguments,
|
||||
index = -1,
|
||||
length = nativeMax(args.length - start, 0),
|
||||
array = Array(length);
|
||||
|
||||
while (++index < length) {
|
||||
array[index] = args[start + index];
|
||||
}
|
||||
switch (start) {
|
||||
case 0: return func.call(this, array);
|
||||
case 1: return func.call(this, args[0], array);
|
||||
case 2: return func.call(this, args[0], args[1], array);
|
||||
}
|
||||
var otherArgs = Array(start + 1);
|
||||
index = -1;
|
||||
while (++index < start) {
|
||||
otherArgs[index] = args[index];
|
||||
}
|
||||
otherArgs[start] = array;
|
||||
return apply(func, this, otherArgs);
|
||||
};
|
||||
start = start === undefined ? start : toInteger(start);
|
||||
return baseRest(func, start);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -10359,7 +10372,7 @@
|
||||
throw new TypeError(FUNC_ERROR_TEXT);
|
||||
}
|
||||
start = start === undefined ? 0 : nativeMax(toInteger(start), 0);
|
||||
return rest(function(args) {
|
||||
return baseRest(function(args) {
|
||||
var array = args[start],
|
||||
otherArgs = castSlice(args, 0, start);
|
||||
|
||||
@@ -12240,7 +12253,7 @@
|
||||
* _.at(object, ['a[0].b.c', 'a[1]']);
|
||||
* // => [3, 4]
|
||||
*/
|
||||
var at = rest(function(object, paths) {
|
||||
var at = baseRest(function(object, paths) {
|
||||
return baseAt(object, baseFlatten(paths, 1));
|
||||
});
|
||||
|
||||
@@ -12304,7 +12317,7 @@
|
||||
* _.defaults({ 'a': 1 }, { 'b': 2 }, { 'a': 3 });
|
||||
* // => { 'a': 1, 'b': 2 }
|
||||
*/
|
||||
var defaults = rest(function(args) {
|
||||
var defaults = baseRest(function(args) {
|
||||
args.push(undefined, assignInDefaults);
|
||||
return apply(assignInWith, undefined, args);
|
||||
});
|
||||
@@ -12328,7 +12341,7 @@
|
||||
* _.defaultsDeep({ 'a': { 'b': 2 } }, { 'a': { 'b': 1, 'c': 3 } });
|
||||
* // => { 'a': { 'b': 2, 'c': 3 } }
|
||||
*/
|
||||
var defaultsDeep = rest(function(args) {
|
||||
var defaultsDeep = baseRest(function(args) {
|
||||
args.push(undefined, mergeDefaults);
|
||||
return apply(mergeWith, undefined, args);
|
||||
});
|
||||
@@ -12758,7 +12771,7 @@
|
||||
* _.invoke(object, 'a[0].b.c.slice', 1, 3);
|
||||
* // => [2, 3]
|
||||
*/
|
||||
var invoke = rest(baseInvoke);
|
||||
var invoke = baseRest(baseInvoke);
|
||||
|
||||
/**
|
||||
* Creates an array of the own enumerable property names of `object`.
|
||||
@@ -13009,7 +13022,7 @@
|
||||
* _.omit(object, ['a', 'c']);
|
||||
* // => { 'b': '2' }
|
||||
*/
|
||||
var omit = rest(function(object, props) {
|
||||
var omit = baseRest(function(object, props) {
|
||||
if (object == null) {
|
||||
return {};
|
||||
}
|
||||
@@ -13061,7 +13074,7 @@
|
||||
* _.pick(object, ['a', 'c']);
|
||||
* // => { 'a': 1, 'c': 3 }
|
||||
*/
|
||||
var pick = rest(function(object, props) {
|
||||
var pick = baseRest(function(object, props) {
|
||||
return object == null ? {} : basePick(object, arrayMap(baseFlatten(props, 1), toKey));
|
||||
});
|
||||
|
||||
@@ -14741,7 +14754,7 @@
|
||||
* elements = [];
|
||||
* }
|
||||
*/
|
||||
var attempt = rest(function(func, args) {
|
||||
var attempt = baseRest(function(func, args) {
|
||||
try {
|
||||
return apply(func, undefined, args);
|
||||
} catch (e) {
|
||||
@@ -14775,7 +14788,7 @@
|
||||
* jQuery(element).on('click', view.click);
|
||||
* // => Logs 'clicked docs' when clicked.
|
||||
*/
|
||||
var bindAll = rest(function(object, methodNames) {
|
||||
var bindAll = baseRest(function(object, methodNames) {
|
||||
arrayEach(baseFlatten(methodNames, 1), function(key) {
|
||||
key = toKey(key);
|
||||
object[key] = bind(object[key], object);
|
||||
@@ -14823,7 +14836,7 @@
|
||||
return [toIteratee(pair[0]), pair[1]];
|
||||
});
|
||||
|
||||
return rest(function(args) {
|
||||
return baseRest(function(args) {
|
||||
var index = -1;
|
||||
while (++index < length) {
|
||||
var pair = pairs[index];
|
||||
@@ -15101,7 +15114,7 @@
|
||||
* _.map(objects, _.method(['a', 'b']));
|
||||
* // => [2, 1]
|
||||
*/
|
||||
var method = rest(function(path, args) {
|
||||
var method = baseRest(function(path, args) {
|
||||
return function(object) {
|
||||
return baseInvoke(object, path, args);
|
||||
};
|
||||
@@ -15130,7 +15143,7 @@
|
||||
* _.map([['a', '2'], ['c', '0']], _.methodOf(object));
|
||||
* // => [2, 0]
|
||||
*/
|
||||
var methodOf = rest(function(object, args) {
|
||||
var methodOf = baseRest(function(object, args) {
|
||||
return function(path) {
|
||||
return baseInvoke(object, path, args);
|
||||
};
|
||||
@@ -15266,7 +15279,7 @@
|
||||
*/
|
||||
function nthArg(n) {
|
||||
n = toInteger(n);
|
||||
return rest(function(args) {
|
||||
return baseRest(function(args) {
|
||||
return baseNth(args, n);
|
||||
});
|
||||
}
|
||||
@@ -16420,7 +16433,7 @@
|
||||
return this.reverse().find(predicate);
|
||||
};
|
||||
|
||||
LazyWrapper.prototype.invokeMap = rest(function(path, args) {
|
||||
LazyWrapper.prototype.invokeMap = baseRest(function(path, args) {
|
||||
if (typeof path == 'function') {
|
||||
return new LazyWrapper(this);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user