UNPKG

62.6 kBJavaScriptView Raw
1/**
2 * lodash (Custom Build) <https://lodash.com/>
3 * Build: `lodash modularize exports="npm" -o ./`
4 * Copyright jQuery Foundation and other contributors <https://jquery.org/>
5 * Released under MIT license <https://lodash.com/license>
6 * Based on Underscore.js 1.8.3 <http://underscorejs.org/LICENSE>
7 * Copyright Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
8 */
9
10/** Used as the size to enable large array optimizations. */
11var LARGE_ARRAY_SIZE = 200;
12
13/** Used as the `TypeError` message for "Functions" methods. */
14var FUNC_ERROR_TEXT = 'Expected a function';
15
16/** Used to stand-in for `undefined` hash values. */
17var HASH_UNDEFINED = '__lodash_hash_undefined__';
18
19/** Used to compose bitmasks for comparison styles. */
20var UNORDERED_COMPARE_FLAG = 1,
21 PARTIAL_COMPARE_FLAG = 2;
22
23/** Used as references for various `Number` constants. */
24var INFINITY = 1 / 0,
25 MAX_SAFE_INTEGER = 9007199254740991;
26
27/** `Object#toString` result references. */
28var argsTag = '[object Arguments]',
29 arrayTag = '[object Array]',
30 boolTag = '[object Boolean]',
31 dateTag = '[object Date]',
32 errorTag = '[object Error]',
33 funcTag = '[object Function]',
34 genTag = '[object GeneratorFunction]',
35 mapTag = '[object Map]',
36 numberTag = '[object Number]',
37 objectTag = '[object Object]',
38 promiseTag = '[object Promise]',
39 regexpTag = '[object RegExp]',
40 setTag = '[object Set]',
41 stringTag = '[object String]',
42 symbolTag = '[object Symbol]',
43 weakMapTag = '[object WeakMap]';
44
45var arrayBufferTag = '[object ArrayBuffer]',
46 dataViewTag = '[object DataView]',
47 float32Tag = '[object Float32Array]',
48 float64Tag = '[object Float64Array]',
49 int8Tag = '[object Int8Array]',
50 int16Tag = '[object Int16Array]',
51 int32Tag = '[object Int32Array]',
52 uint8Tag = '[object Uint8Array]',
53 uint8ClampedTag = '[object Uint8ClampedArray]',
54 uint16Tag = '[object Uint16Array]',
55 uint32Tag = '[object Uint32Array]';
56
57/** Used to match property names within property paths. */
58var reIsDeepProp = /\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\\]|\\.)*?\1)\]/,
59 reIsPlainProp = /^\w*$/,
60 reLeadingDot = /^\./,
61 rePropName = /[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\\]|\\.)*?)\2)\]|(?=(?:\.|\[\])(?:\.|\[\]|$))/g;
62
63/**
64 * Used to match `RegExp`
65 * [syntax characters](http://ecma-international.org/ecma-262/6.0/#sec-patterns).
66 */
67var reRegExpChar = /[\\^$.*+?()[\]{}|]/g;
68
69/** Used to match backslashes in property paths. */
70var reEscapeChar = /\\(\\)?/g;
71
72/** Used to detect host constructors (Safari). */
73var reIsHostCtor = /^\[object .+?Constructor\]$/;
74
75/** Used to detect unsigned integer values. */
76var reIsUint = /^(?:0|[1-9]\d*)$/;
77
78/** Used to identify `toStringTag` values of typed arrays. */
79var typedArrayTags = {};
80typedArrayTags[float32Tag] = typedArrayTags[float64Tag] =
81typedArrayTags[int8Tag] = typedArrayTags[int16Tag] =
82typedArrayTags[int32Tag] = typedArrayTags[uint8Tag] =
83typedArrayTags[uint8ClampedTag] = typedArrayTags[uint16Tag] =
84typedArrayTags[uint32Tag] = true;
85typedArrayTags[argsTag] = typedArrayTags[arrayTag] =
86typedArrayTags[arrayBufferTag] = typedArrayTags[boolTag] =
87typedArrayTags[dataViewTag] = typedArrayTags[dateTag] =
88typedArrayTags[errorTag] = typedArrayTags[funcTag] =
89typedArrayTags[mapTag] = typedArrayTags[numberTag] =
90typedArrayTags[objectTag] = typedArrayTags[regexpTag] =
91typedArrayTags[setTag] = typedArrayTags[stringTag] =
92typedArrayTags[weakMapTag] = false;
93
94/** Detect free variable `global` from Node.js. */
95var freeGlobal = typeof global == 'object' && global && global.Object === Object && global;
96
97/** Detect free variable `self`. */
98var freeSelf = typeof self == 'object' && self && self.Object === Object && self;
99
100/** Used as a reference to the global object. */
101var root = freeGlobal || freeSelf || Function('return this')();
102
103/** Detect free variable `exports`. */
104var freeExports = typeof exports == 'object' && exports && !exports.nodeType && exports;
105
106/** Detect free variable `module`. */
107var freeModule = freeExports && typeof module == 'object' && module && !module.nodeType && module;
108
109/** Detect the popular CommonJS extension `module.exports`. */
110var moduleExports = freeModule && freeModule.exports === freeExports;
111
112/** Detect free variable `process` from Node.js. */
113var freeProcess = moduleExports && freeGlobal.process;
114
115/** Used to access faster Node.js helpers. */
116var nodeUtil = (function() {
117 try {
118 return freeProcess && freeProcess.binding('util');
119 } catch (e) {}
120}());
121
122/* Node.js helper references. */
123var nodeIsTypedArray = nodeUtil && nodeUtil.isTypedArray;
124
125/**
126 * A specialized version of `_.some` for arrays without support for iteratee
127 * shorthands.
128 *
129 * @private
130 * @param {Array} [array] The array to iterate over.
131 * @param {Function} predicate The function invoked per iteration.
132 * @returns {boolean} Returns `true` if any element passes the predicate check,
133 * else `false`.
134 */
135function arraySome(array, predicate) {
136 var index = -1,
137 length = array ? array.length : 0;
138
139 while (++index < length) {
140 if (predicate(array[index], index, array)) {
141 return true;
142 }
143 }
144 return false;
145}
146
147/**
148 * The base implementation of `_.property` without support for deep paths.
149 *
150 * @private
151 * @param {string} key The key of the property to get.
152 * @returns {Function} Returns the new accessor function.
153 */
154function baseProperty(key) {
155 return function(object) {
156 return object == null ? undefined : object[key];
157 };
158}
159
160/**
161 * The base implementation of `_.times` without support for iteratee shorthands
162 * or max array length checks.
163 *
164 * @private
165 * @param {number} n The number of times to invoke `iteratee`.
166 * @param {Function} iteratee The function invoked per iteration.
167 * @returns {Array} Returns the array of results.
168 */
169function baseTimes(n, iteratee) {
170 var index = -1,
171 result = Array(n);
172
173 while (++index < n) {
174 result[index] = iteratee(index);
175 }
176 return result;
177}
178
179/**
180 * The base implementation of `_.unary` without support for storing metadata.
181 *
182 * @private
183 * @param {Function} func The function to cap arguments for.
184 * @returns {Function} Returns the new capped function.
185 */
186function baseUnary(func) {
187 return function(value) {
188 return func(value);
189 };
190}
191
192/**
193 * Gets the value at `key` of `object`.
194 *
195 * @private
196 * @param {Object} [object] The object to query.
197 * @param {string} key The key of the property to get.
198 * @returns {*} Returns the property value.
199 */
200function getValue(object, key) {
201 return object == null ? undefined : object[key];
202}
203
204/**
205 * Checks if `value` is a host object in IE < 9.
206 *
207 * @private
208 * @param {*} value The value to check.
209 * @returns {boolean} Returns `true` if `value` is a host object, else `false`.
210 */
211function isHostObject(value) {
212 // Many host objects are `Object` objects that can coerce to strings
213 // despite having improperly defined `toString` methods.
214 var result = false;
215 if (value != null && typeof value.toString != 'function') {
216 try {
217 result = !!(value + '');
218 } catch (e) {}
219 }
220 return result;
221}
222
223/**
224 * Converts `map` to its key-value pairs.
225 *
226 * @private
227 * @param {Object} map The map to convert.
228 * @returns {Array} Returns the key-value pairs.
229 */
230function mapToArray(map) {
231 var index = -1,
232 result = Array(map.size);
233
234 map.forEach(function(value, key) {
235 result[++index] = [key, value];
236 });
237 return result;
238}
239
240/**
241 * Creates a function that invokes `func` with its first argument transformed.
242 *
243 * @private
244 * @param {Function} func The function to wrap.
245 * @param {Function} transform The argument transform.
246 * @returns {Function} Returns the new function.
247 */
248function overArg(func, transform) {
249 return function(arg) {
250 return func(transform(arg));
251 };
252}
253
254/**
255 * Converts `set` to an array of its values.
256 *
257 * @private
258 * @param {Object} set The set to convert.
259 * @returns {Array} Returns the values.
260 */
261function setToArray(set) {
262 var index = -1,
263 result = Array(set.size);
264
265 set.forEach(function(value) {
266 result[++index] = value;
267 });
268 return result;
269}
270
271/** Used for built-in method references. */
272var arrayProto = Array.prototype,
273 objectProto = Object.prototype;
274
275/** Used to detect overreaching core-js shims. */
276var coreJsData = root['__core-js_shared__'];
277
278/** Used to detect methods masquerading as native. */
279var maskSrcKey = (function() {
280 var uid = /[^.]+$/.exec(coreJsData && coreJsData.keys && coreJsData.keys.IE_PROTO || '');
281 return uid ? ('Symbol(src)_1.' + uid) : '';
282}());
283
284/** Used to resolve the decompiled source of functions. */
285var funcToString = Function.prototype.toString;
286
287/** Used to check objects for own properties. */
288var hasOwnProperty = objectProto.hasOwnProperty;
289
290/**
291 * Used to resolve the
292 * [`toStringTag`](http://ecma-international.org/ecma-262/6.0/#sec-object.prototype.tostring)
293 * of values.
294 */
295var objectToString = objectProto.toString;
296
297/** Used to detect if a method is native. */
298var reIsNative = RegExp('^' +
299 funcToString.call(hasOwnProperty).replace(reRegExpChar, '\\$&')
300 .replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g, '$1.*?') + '$'
301);
302
303/** Built-in value references. */
304var Symbol = root.Symbol,
305 Uint8Array = root.Uint8Array,
306 propertyIsEnumerable = objectProto.propertyIsEnumerable,
307 splice = arrayProto.splice;
308
309/* Built-in method references for those with the same name as other `lodash` methods. */
310var nativeGetPrototype = Object.getPrototypeOf,
311 nativeKeys = Object.keys;
312
313/* Built-in method references that are verified to be native. */
314var DataView = getNative(root, 'DataView'),
315 Map = getNative(root, 'Map'),
316 Promise = getNative(root, 'Promise'),
317 Set = getNative(root, 'Set'),
318 WeakMap = getNative(root, 'WeakMap'),
319 nativeCreate = getNative(Object, 'create');
320
321/** Used to detect maps, sets, and weakmaps. */
322var dataViewCtorString = toSource(DataView),
323 mapCtorString = toSource(Map),
324 promiseCtorString = toSource(Promise),
325 setCtorString = toSource(Set),
326 weakMapCtorString = toSource(WeakMap);
327
328/** Used to convert symbols to primitives and strings. */
329var symbolProto = Symbol ? Symbol.prototype : undefined,
330 symbolValueOf = symbolProto ? symbolProto.valueOf : undefined,
331 symbolToString = symbolProto ? symbolProto.toString : undefined;
332
333/**
334 * Creates a hash object.
335 *
336 * @private
337 * @constructor
338 * @param {Array} [entries] The key-value pairs to cache.
339 */
340function Hash(entries) {
341 var index = -1,
342 length = entries ? entries.length : 0;
343
344 this.clear();
345 while (++index < length) {
346 var entry = entries[index];
347 this.set(entry[0], entry[1]);
348 }
349}
350
351/**
352 * Removes all key-value entries from the hash.
353 *
354 * @private
355 * @name clear
356 * @memberOf Hash
357 */
358function hashClear() {
359 this.__data__ = nativeCreate ? nativeCreate(null) : {};
360}
361
362/**
363 * Removes `key` and its value from the hash.
364 *
365 * @private
366 * @name delete
367 * @memberOf Hash
368 * @param {Object} hash The hash to modify.
369 * @param {string} key The key of the value to remove.
370 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
371 */
372function hashDelete(key) {
373 return this.has(key) && delete this.__data__[key];
374}
375
376/**
377 * Gets the hash value for `key`.
378 *
379 * @private
380 * @name get
381 * @memberOf Hash
382 * @param {string} key The key of the value to get.
383 * @returns {*} Returns the entry value.
384 */
385function hashGet(key) {
386 var data = this.__data__;
387 if (nativeCreate) {
388 var result = data[key];
389 return result === HASH_UNDEFINED ? undefined : result;
390 }
391 return hasOwnProperty.call(data, key) ? data[key] : undefined;
392}
393
394/**
395 * Checks if a hash value for `key` exists.
396 *
397 * @private
398 * @name has
399 * @memberOf Hash
400 * @param {string} key The key of the entry to check.
401 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
402 */
403function hashHas(key) {
404 var data = this.__data__;
405 return nativeCreate ? data[key] !== undefined : hasOwnProperty.call(data, key);
406}
407
408/**
409 * Sets the hash `key` to `value`.
410 *
411 * @private
412 * @name set
413 * @memberOf Hash
414 * @param {string} key The key of the value to set.
415 * @param {*} value The value to set.
416 * @returns {Object} Returns the hash instance.
417 */
418function hashSet(key, value) {
419 var data = this.__data__;
420 data[key] = (nativeCreate && value === undefined) ? HASH_UNDEFINED : value;
421 return this;
422}
423
424// Add methods to `Hash`.
425Hash.prototype.clear = hashClear;
426Hash.prototype['delete'] = hashDelete;
427Hash.prototype.get = hashGet;
428Hash.prototype.has = hashHas;
429Hash.prototype.set = hashSet;
430
431/**
432 * Creates an list cache object.
433 *
434 * @private
435 * @constructor
436 * @param {Array} [entries] The key-value pairs to cache.
437 */
438function ListCache(entries) {
439 var index = -1,
440 length = entries ? entries.length : 0;
441
442 this.clear();
443 while (++index < length) {
444 var entry = entries[index];
445 this.set(entry[0], entry[1]);
446 }
447}
448
449/**
450 * Removes all key-value entries from the list cache.
451 *
452 * @private
453 * @name clear
454 * @memberOf ListCache
455 */
456function listCacheClear() {
457 this.__data__ = [];
458}
459
460/**
461 * Removes `key` and its value from the list cache.
462 *
463 * @private
464 * @name delete
465 * @memberOf ListCache
466 * @param {string} key The key of the value to remove.
467 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
468 */
469function listCacheDelete(key) {
470 var data = this.__data__,
471 index = assocIndexOf(data, key);
472
473 if (index < 0) {
474 return false;
475 }
476 var lastIndex = data.length - 1;
477 if (index == lastIndex) {
478 data.pop();
479 } else {
480 splice.call(data, index, 1);
481 }
482 return true;
483}
484
485/**
486 * Gets the list cache value for `key`.
487 *
488 * @private
489 * @name get
490 * @memberOf ListCache
491 * @param {string} key The key of the value to get.
492 * @returns {*} Returns the entry value.
493 */
494function listCacheGet(key) {
495 var data = this.__data__,
496 index = assocIndexOf(data, key);
497
498 return index < 0 ? undefined : data[index][1];
499}
500
501/**
502 * Checks if a list cache value for `key` exists.
503 *
504 * @private
505 * @name has
506 * @memberOf ListCache
507 * @param {string} key The key of the entry to check.
508 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
509 */
510function listCacheHas(key) {
511 return assocIndexOf(this.__data__, key) > -1;
512}
513
514/**
515 * Sets the list cache `key` to `value`.
516 *
517 * @private
518 * @name set
519 * @memberOf ListCache
520 * @param {string} key The key of the value to set.
521 * @param {*} value The value to set.
522 * @returns {Object} Returns the list cache instance.
523 */
524function listCacheSet(key, value) {
525 var data = this.__data__,
526 index = assocIndexOf(data, key);
527
528 if (index < 0) {
529 data.push([key, value]);
530 } else {
531 data[index][1] = value;
532 }
533 return this;
534}
535
536// Add methods to `ListCache`.
537ListCache.prototype.clear = listCacheClear;
538ListCache.prototype['delete'] = listCacheDelete;
539ListCache.prototype.get = listCacheGet;
540ListCache.prototype.has = listCacheHas;
541ListCache.prototype.set = listCacheSet;
542
543/**
544 * Creates a map cache object to store key-value pairs.
545 *
546 * @private
547 * @constructor
548 * @param {Array} [entries] The key-value pairs to cache.
549 */
550function MapCache(entries) {
551 var index = -1,
552 length = entries ? entries.length : 0;
553
554 this.clear();
555 while (++index < length) {
556 var entry = entries[index];
557 this.set(entry[0], entry[1]);
558 }
559}
560
561/**
562 * Removes all key-value entries from the map.
563 *
564 * @private
565 * @name clear
566 * @memberOf MapCache
567 */
568function mapCacheClear() {
569 this.__data__ = {
570 'hash': new Hash,
571 'map': new (Map || ListCache),
572 'string': new Hash
573 };
574}
575
576/**
577 * Removes `key` and its value from the map.
578 *
579 * @private
580 * @name delete
581 * @memberOf MapCache
582 * @param {string} key The key of the value to remove.
583 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
584 */
585function mapCacheDelete(key) {
586 return getMapData(this, key)['delete'](key);
587}
588
589/**
590 * Gets the map value for `key`.
591 *
592 * @private
593 * @name get
594 * @memberOf MapCache
595 * @param {string} key The key of the value to get.
596 * @returns {*} Returns the entry value.
597 */
598function mapCacheGet(key) {
599 return getMapData(this, key).get(key);
600}
601
602/**
603 * Checks if a map value for `key` exists.
604 *
605 * @private
606 * @name has
607 * @memberOf MapCache
608 * @param {string} key The key of the entry to check.
609 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
610 */
611function mapCacheHas(key) {
612 return getMapData(this, key).has(key);
613}
614
615/**
616 * Sets the map `key` to `value`.
617 *
618 * @private
619 * @name set
620 * @memberOf MapCache
621 * @param {string} key The key of the value to set.
622 * @param {*} value The value to set.
623 * @returns {Object} Returns the map cache instance.
624 */
625function mapCacheSet(key, value) {
626 getMapData(this, key).set(key, value);
627 return this;
628}
629
630// Add methods to `MapCache`.
631MapCache.prototype.clear = mapCacheClear;
632MapCache.prototype['delete'] = mapCacheDelete;
633MapCache.prototype.get = mapCacheGet;
634MapCache.prototype.has = mapCacheHas;
635MapCache.prototype.set = mapCacheSet;
636
637/**
638 *
639 * Creates an array cache object to store unique values.
640 *
641 * @private
642 * @constructor
643 * @param {Array} [values] The values to cache.
644 */
645function SetCache(values) {
646 var index = -1,
647 length = values ? values.length : 0;
648
649 this.__data__ = new MapCache;
650 while (++index < length) {
651 this.add(values[index]);
652 }
653}
654
655/**
656 * Adds `value` to the array cache.
657 *
658 * @private
659 * @name add
660 * @memberOf SetCache
661 * @alias push
662 * @param {*} value The value to cache.
663 * @returns {Object} Returns the cache instance.
664 */
665function setCacheAdd(value) {
666 this.__data__.set(value, HASH_UNDEFINED);
667 return this;
668}
669
670/**
671 * Checks if `value` is in the array cache.
672 *
673 * @private
674 * @name has
675 * @memberOf SetCache
676 * @param {*} value The value to search for.
677 * @returns {number} Returns `true` if `value` is found, else `false`.
678 */
679function setCacheHas(value) {
680 return this.__data__.has(value);
681}
682
683// Add methods to `SetCache`.
684SetCache.prototype.add = SetCache.prototype.push = setCacheAdd;
685SetCache.prototype.has = setCacheHas;
686
687/**
688 * Creates a stack cache object to store key-value pairs.
689 *
690 * @private
691 * @constructor
692 * @param {Array} [entries] The key-value pairs to cache.
693 */
694function Stack(entries) {
695 this.__data__ = new ListCache(entries);
696}
697
698/**
699 * Removes all key-value entries from the stack.
700 *
701 * @private
702 * @name clear
703 * @memberOf Stack
704 */
705function stackClear() {
706 this.__data__ = new ListCache;
707}
708
709/**
710 * Removes `key` and its value from the stack.
711 *
712 * @private
713 * @name delete
714 * @memberOf Stack
715 * @param {string} key The key of the value to remove.
716 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
717 */
718function stackDelete(key) {
719 return this.__data__['delete'](key);
720}
721
722/**
723 * Gets the stack value for `key`.
724 *
725 * @private
726 * @name get
727 * @memberOf Stack
728 * @param {string} key The key of the value to get.
729 * @returns {*} Returns the entry value.
730 */
731function stackGet(key) {
732 return this.__data__.get(key);
733}
734
735/**
736 * Checks if a stack value for `key` exists.
737 *
738 * @private
739 * @name has
740 * @memberOf Stack
741 * @param {string} key The key of the entry to check.
742 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
743 */
744function stackHas(key) {
745 return this.__data__.has(key);
746}
747
748/**
749 * Sets the stack `key` to `value`.
750 *
751 * @private
752 * @name set
753 * @memberOf Stack
754 * @param {string} key The key of the value to set.
755 * @param {*} value The value to set.
756 * @returns {Object} Returns the stack cache instance.
757 */
758function stackSet(key, value) {
759 var cache = this.__data__;
760 if (cache instanceof ListCache) {
761 var pairs = cache.__data__;
762 if (!Map || (pairs.length < LARGE_ARRAY_SIZE - 1)) {
763 pairs.push([key, value]);
764 return this;
765 }
766 cache = this.__data__ = new MapCache(pairs);
767 }
768 cache.set(key, value);
769 return this;
770}
771
772// Add methods to `Stack`.
773Stack.prototype.clear = stackClear;
774Stack.prototype['delete'] = stackDelete;
775Stack.prototype.get = stackGet;
776Stack.prototype.has = stackHas;
777Stack.prototype.set = stackSet;
778
779/**
780 * Gets the index at which the `key` is found in `array` of key-value pairs.
781 *
782 * @private
783 * @param {Array} array The array to search.
784 * @param {*} key The key to search for.
785 * @returns {number} Returns the index of the matched value, else `-1`.
786 */
787function assocIndexOf(array, key) {
788 var length = array.length;
789 while (length--) {
790 if (eq(array[length][0], key)) {
791 return length;
792 }
793 }
794 return -1;
795}
796
797/**
798 * The base implementation of methods like `_.max` and `_.min` which accepts a
799 * `comparator` to determine the extremum value.
800 *
801 * @private
802 * @param {Array} array The array to iterate over.
803 * @param {Function} iteratee The iteratee invoked per iteration.
804 * @param {Function} comparator The comparator used to compare values.
805 * @returns {*} Returns the extremum value.
806 */
807function baseExtremum(array, iteratee, comparator) {
808 var index = -1,
809 length = array.length;
810
811 while (++index < length) {
812 var value = array[index],
813 current = iteratee(value);
814
815 if (current != null && (computed === undefined
816 ? (current === current && !isSymbol(current))
817 : comparator(current, computed)
818 )) {
819 var computed = current,
820 result = value;
821 }
822 }
823 return result;
824}
825
826/**
827 * The base implementation of `_.get` without support for default values.
828 *
829 * @private
830 * @param {Object} object The object to query.
831 * @param {Array|string} path The path of the property to get.
832 * @returns {*} Returns the resolved value.
833 */
834function baseGet(object, path) {
835 path = isKey(path, object) ? [path] : castPath(path);
836
837 var index = 0,
838 length = path.length;
839
840 while (object != null && index < length) {
841 object = object[toKey(path[index++])];
842 }
843 return (index && index == length) ? object : undefined;
844}
845
846/**
847 * The base implementation of `getTag`.
848 *
849 * @private
850 * @param {*} value The value to query.
851 * @returns {string} Returns the `toStringTag`.
852 */
853function baseGetTag(value) {
854 return objectToString.call(value);
855}
856
857/**
858 * The base implementation of `_.has` without support for deep paths.
859 *
860 * @private
861 * @param {Object} [object] The object to query.
862 * @param {Array|string} key The key to check.
863 * @returns {boolean} Returns `true` if `key` exists, else `false`.
864 */
865function baseHas(object, key) {
866 // Avoid a bug in IE 10-11 where objects with a [[Prototype]] of `null`,
867 // that are composed entirely of index properties, return `false` for
868 // `hasOwnProperty` checks of them.
869 return object != null &&
870 (hasOwnProperty.call(object, key) ||
871 (typeof object == 'object' && key in object && getPrototype(object) === null));
872}
873
874/**
875 * The base implementation of `_.hasIn` without support for deep paths.
876 *
877 * @private
878 * @param {Object} [object] The object to query.
879 * @param {Array|string} key The key to check.
880 * @returns {boolean} Returns `true` if `key` exists, else `false`.
881 */
882function baseHasIn(object, key) {
883 return object != null && key in Object(object);
884}
885
886/**
887 * The base implementation of `_.isEqual` which supports partial comparisons
888 * and tracks traversed objects.
889 *
890 * @private
891 * @param {*} value The value to compare.
892 * @param {*} other The other value to compare.
893 * @param {Function} [customizer] The function to customize comparisons.
894 * @param {boolean} [bitmask] The bitmask of comparison flags.
895 * The bitmask may be composed of the following flags:
896 * 1 - Unordered comparison
897 * 2 - Partial comparison
898 * @param {Object} [stack] Tracks traversed `value` and `other` objects.
899 * @returns {boolean} Returns `true` if the values are equivalent, else `false`.
900 */
901function baseIsEqual(value, other, customizer, bitmask, stack) {
902 if (value === other) {
903 return true;
904 }
905 if (value == null || other == null || (!isObject(value) && !isObjectLike(other))) {
906 return value !== value && other !== other;
907 }
908 return baseIsEqualDeep(value, other, baseIsEqual, customizer, bitmask, stack);
909}
910
911/**
912 * A specialized version of `baseIsEqual` for arrays and objects which performs
913 * deep comparisons and tracks traversed objects enabling objects with circular
914 * references to be compared.
915 *
916 * @private
917 * @param {Object} object The object to compare.
918 * @param {Object} other The other object to compare.
919 * @param {Function} equalFunc The function to determine equivalents of values.
920 * @param {Function} [customizer] The function to customize comparisons.
921 * @param {number} [bitmask] The bitmask of comparison flags. See `baseIsEqual`
922 * for more details.
923 * @param {Object} [stack] Tracks traversed `object` and `other` objects.
924 * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
925 */
926function baseIsEqualDeep(object, other, equalFunc, customizer, bitmask, stack) {
927 var objIsArr = isArray(object),
928 othIsArr = isArray(other),
929 objTag = arrayTag,
930 othTag = arrayTag;
931
932 if (!objIsArr) {
933 objTag = getTag(object);
934 objTag = objTag == argsTag ? objectTag : objTag;
935 }
936 if (!othIsArr) {
937 othTag = getTag(other);
938 othTag = othTag == argsTag ? objectTag : othTag;
939 }
940 var objIsObj = objTag == objectTag && !isHostObject(object),
941 othIsObj = othTag == objectTag && !isHostObject(other),
942 isSameTag = objTag == othTag;
943
944 if (isSameTag && !objIsObj) {
945 stack || (stack = new Stack);
946 return (objIsArr || isTypedArray(object))
947 ? equalArrays(object, other, equalFunc, customizer, bitmask, stack)
948 : equalByTag(object, other, objTag, equalFunc, customizer, bitmask, stack);
949 }
950 if (!(bitmask & PARTIAL_COMPARE_FLAG)) {
951 var objIsWrapped = objIsObj && hasOwnProperty.call(object, '__wrapped__'),
952 othIsWrapped = othIsObj && hasOwnProperty.call(other, '__wrapped__');
953
954 if (objIsWrapped || othIsWrapped) {
955 var objUnwrapped = objIsWrapped ? object.value() : object,
956 othUnwrapped = othIsWrapped ? other.value() : other;
957
958 stack || (stack = new Stack);
959 return equalFunc(objUnwrapped, othUnwrapped, customizer, bitmask, stack);
960 }
961 }
962 if (!isSameTag) {
963 return false;
964 }
965 stack || (stack = new Stack);
966 return equalObjects(object, other, equalFunc, customizer, bitmask, stack);
967}
968
969/**
970 * The base implementation of `_.isMatch` without support for iteratee shorthands.
971 *
972 * @private
973 * @param {Object} object The object to inspect.
974 * @param {Object} source The object of property values to match.
975 * @param {Array} matchData The property names, values, and compare flags to match.
976 * @param {Function} [customizer] The function to customize comparisons.
977 * @returns {boolean} Returns `true` if `object` is a match, else `false`.
978 */
979function baseIsMatch(object, source, matchData, customizer) {
980 var index = matchData.length,
981 length = index,
982 noCustomizer = !customizer;
983
984 if (object == null) {
985 return !length;
986 }
987 object = Object(object);
988 while (index--) {
989 var data = matchData[index];
990 if ((noCustomizer && data[2])
991 ? data[1] !== object[data[0]]
992 : !(data[0] in object)
993 ) {
994 return false;
995 }
996 }
997 while (++index < length) {
998 data = matchData[index];
999 var key = data[0],
1000 objValue = object[key],
1001 srcValue = data[1];
1002
1003 if (noCustomizer && data[2]) {
1004 if (objValue === undefined && !(key in object)) {
1005 return false;
1006 }
1007 } else {
1008 var stack = new Stack;
1009 if (customizer) {
1010 var result = customizer(objValue, srcValue, key, object, source, stack);
1011 }
1012 if (!(result === undefined
1013 ? baseIsEqual(srcValue, objValue, customizer, UNORDERED_COMPARE_FLAG | PARTIAL_COMPARE_FLAG, stack)
1014 : result
1015 )) {
1016 return false;
1017 }
1018 }
1019 }
1020 return true;
1021}
1022
1023/**
1024 * The base implementation of `_.isNative` without bad shim checks.
1025 *
1026 * @private
1027 * @param {*} value The value to check.
1028 * @returns {boolean} Returns `true` if `value` is a native function,
1029 * else `false`.
1030 */
1031function baseIsNative(value) {
1032 if (!isObject(value) || isMasked(value)) {
1033 return false;
1034 }
1035 var pattern = (isFunction(value) || isHostObject(value)) ? reIsNative : reIsHostCtor;
1036 return pattern.test(toSource(value));
1037}
1038
1039/**
1040 * The base implementation of `_.isTypedArray` without Node.js optimizations.
1041 *
1042 * @private
1043 * @param {*} value The value to check.
1044 * @returns {boolean} Returns `true` if `value` is a typed array, else `false`.
1045 */
1046function baseIsTypedArray(value) {
1047 return isObjectLike(value) &&
1048 isLength(value.length) && !!typedArrayTags[objectToString.call(value)];
1049}
1050
1051/**
1052 * The base implementation of `_.iteratee`.
1053 *
1054 * @private
1055 * @param {*} [value=_.identity] The value to convert to an iteratee.
1056 * @returns {Function} Returns the iteratee.
1057 */
1058function baseIteratee(value) {
1059 // Don't store the `typeof` result in a variable to avoid a JIT bug in Safari 9.
1060 // See https://bugs.webkit.org/show_bug.cgi?id=156034 for more details.
1061 if (typeof value == 'function') {
1062 return value;
1063 }
1064 if (value == null) {
1065 return identity;
1066 }
1067 if (typeof value == 'object') {
1068 return isArray(value)
1069 ? baseMatchesProperty(value[0], value[1])
1070 : baseMatches(value);
1071 }
1072 return property(value);
1073}
1074
1075/**
1076 * The base implementation of `_.keys` which doesn't skip the constructor
1077 * property of prototypes or treat sparse arrays as dense.
1078 *
1079 * @private
1080 * @param {Object} object The object to query.
1081 * @returns {Array} Returns the array of property names.
1082 */
1083var baseKeys = overArg(nativeKeys, Object);
1084
1085/**
1086 * The base implementation of `_.lt` which doesn't coerce arguments.
1087 *
1088 * @private
1089 * @param {*} value The value to compare.
1090 * @param {*} other The other value to compare.
1091 * @returns {boolean} Returns `true` if `value` is less than `other`,
1092 * else `false`.
1093 */
1094function baseLt(value, other) {
1095 return value < other;
1096}
1097
1098/**
1099 * The base implementation of `_.matches` which doesn't clone `source`.
1100 *
1101 * @private
1102 * @param {Object} source The object of property values to match.
1103 * @returns {Function} Returns the new spec function.
1104 */
1105function baseMatches(source) {
1106 var matchData = getMatchData(source);
1107 if (matchData.length == 1 && matchData[0][2]) {
1108 return matchesStrictComparable(matchData[0][0], matchData[0][1]);
1109 }
1110 return function(object) {
1111 return object === source || baseIsMatch(object, source, matchData);
1112 };
1113}
1114
1115/**
1116 * The base implementation of `_.matchesProperty` which doesn't clone `srcValue`.
1117 *
1118 * @private
1119 * @param {string} path The path of the property to get.
1120 * @param {*} srcValue The value to match.
1121 * @returns {Function} Returns the new spec function.
1122 */
1123function baseMatchesProperty(path, srcValue) {
1124 if (isKey(path) && isStrictComparable(srcValue)) {
1125 return matchesStrictComparable(toKey(path), srcValue);
1126 }
1127 return function(object) {
1128 var objValue = get(object, path);
1129 return (objValue === undefined && objValue === srcValue)
1130 ? hasIn(object, path)
1131 : baseIsEqual(srcValue, objValue, undefined, UNORDERED_COMPARE_FLAG | PARTIAL_COMPARE_FLAG);
1132 };
1133}
1134
1135/**
1136 * A specialized version of `baseProperty` which supports deep paths.
1137 *
1138 * @private
1139 * @param {Array|string} path The path of the property to get.
1140 * @returns {Function} Returns the new accessor function.
1141 */
1142function basePropertyDeep(path) {
1143 return function(object) {
1144 return baseGet(object, path);
1145 };
1146}
1147
1148/**
1149 * The base implementation of `_.toString` which doesn't convert nullish
1150 * values to empty strings.
1151 *
1152 * @private
1153 * @param {*} value The value to process.
1154 * @returns {string} Returns the string.
1155 */
1156function baseToString(value) {
1157 // Exit early for strings to avoid a performance hit in some environments.
1158 if (typeof value == 'string') {
1159 return value;
1160 }
1161 if (isSymbol(value)) {
1162 return symbolToString ? symbolToString.call(value) : '';
1163 }
1164 var result = (value + '');
1165 return (result == '0' && (1 / value) == -INFINITY) ? '-0' : result;
1166}
1167
1168/**
1169 * Casts `value` to a path array if it's not one.
1170 *
1171 * @private
1172 * @param {*} value The value to inspect.
1173 * @returns {Array} Returns the cast property path array.
1174 */
1175function castPath(value) {
1176 return isArray(value) ? value : stringToPath(value);
1177}
1178
1179/**
1180 * A specialized version of `baseIsEqualDeep` for arrays with support for
1181 * partial deep comparisons.
1182 *
1183 * @private
1184 * @param {Array} array The array to compare.
1185 * @param {Array} other The other array to compare.
1186 * @param {Function} equalFunc The function to determine equivalents of values.
1187 * @param {Function} customizer The function to customize comparisons.
1188 * @param {number} bitmask The bitmask of comparison flags. See `baseIsEqual`
1189 * for more details.
1190 * @param {Object} stack Tracks traversed `array` and `other` objects.
1191 * @returns {boolean} Returns `true` if the arrays are equivalent, else `false`.
1192 */
1193function equalArrays(array, other, equalFunc, customizer, bitmask, stack) {
1194 var isPartial = bitmask & PARTIAL_COMPARE_FLAG,
1195 arrLength = array.length,
1196 othLength = other.length;
1197
1198 if (arrLength != othLength && !(isPartial && othLength > arrLength)) {
1199 return false;
1200 }
1201 // Assume cyclic values are equal.
1202 var stacked = stack.get(array);
1203 if (stacked && stack.get(other)) {
1204 return stacked == other;
1205 }
1206 var index = -1,
1207 result = true,
1208 seen = (bitmask & UNORDERED_COMPARE_FLAG) ? new SetCache : undefined;
1209
1210 stack.set(array, other);
1211 stack.set(other, array);
1212
1213 // Ignore non-index properties.
1214 while (++index < arrLength) {
1215 var arrValue = array[index],
1216 othValue = other[index];
1217
1218 if (customizer) {
1219 var compared = isPartial
1220 ? customizer(othValue, arrValue, index, other, array, stack)
1221 : customizer(arrValue, othValue, index, array, other, stack);
1222 }
1223 if (compared !== undefined) {
1224 if (compared) {
1225 continue;
1226 }
1227 result = false;
1228 break;
1229 }
1230 // Recursively compare arrays (susceptible to call stack limits).
1231 if (seen) {
1232 if (!arraySome(other, function(othValue, othIndex) {
1233 if (!seen.has(othIndex) &&
1234 (arrValue === othValue || equalFunc(arrValue, othValue, customizer, bitmask, stack))) {
1235 return seen.add(othIndex);
1236 }
1237 })) {
1238 result = false;
1239 break;
1240 }
1241 } else if (!(
1242 arrValue === othValue ||
1243 equalFunc(arrValue, othValue, customizer, bitmask, stack)
1244 )) {
1245 result = false;
1246 break;
1247 }
1248 }
1249 stack['delete'](array);
1250 stack['delete'](other);
1251 return result;
1252}
1253
1254/**
1255 * A specialized version of `baseIsEqualDeep` for comparing objects of
1256 * the same `toStringTag`.
1257 *
1258 * **Note:** This function only supports comparing values with tags of
1259 * `Boolean`, `Date`, `Error`, `Number`, `RegExp`, or `String`.
1260 *
1261 * @private
1262 * @param {Object} object The object to compare.
1263 * @param {Object} other The other object to compare.
1264 * @param {string} tag The `toStringTag` of the objects to compare.
1265 * @param {Function} equalFunc The function to determine equivalents of values.
1266 * @param {Function} customizer The function to customize comparisons.
1267 * @param {number} bitmask The bitmask of comparison flags. See `baseIsEqual`
1268 * for more details.
1269 * @param {Object} stack Tracks traversed `object` and `other` objects.
1270 * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
1271 */
1272function equalByTag(object, other, tag, equalFunc, customizer, bitmask, stack) {
1273 switch (tag) {
1274 case dataViewTag:
1275 if ((object.byteLength != other.byteLength) ||
1276 (object.byteOffset != other.byteOffset)) {
1277 return false;
1278 }
1279 object = object.buffer;
1280 other = other.buffer;
1281
1282 case arrayBufferTag:
1283 if ((object.byteLength != other.byteLength) ||
1284 !equalFunc(new Uint8Array(object), new Uint8Array(other))) {
1285 return false;
1286 }
1287 return true;
1288
1289 case boolTag:
1290 case dateTag:
1291 case numberTag:
1292 // Coerce booleans to `1` or `0` and dates to milliseconds.
1293 // Invalid dates are coerced to `NaN`.
1294 return eq(+object, +other);
1295
1296 case errorTag:
1297 return object.name == other.name && object.message == other.message;
1298
1299 case regexpTag:
1300 case stringTag:
1301 // Coerce regexes to strings and treat strings, primitives and objects,
1302 // as equal. See http://www.ecma-international.org/ecma-262/6.0/#sec-regexp.prototype.tostring
1303 // for more details.
1304 return object == (other + '');
1305
1306 case mapTag:
1307 var convert = mapToArray;
1308
1309 case setTag:
1310 var isPartial = bitmask & PARTIAL_COMPARE_FLAG;
1311 convert || (convert = setToArray);
1312
1313 if (object.size != other.size && !isPartial) {
1314 return false;
1315 }
1316 // Assume cyclic values are equal.
1317 var stacked = stack.get(object);
1318 if (stacked) {
1319 return stacked == other;
1320 }
1321 bitmask |= UNORDERED_COMPARE_FLAG;
1322
1323 // Recursively compare objects (susceptible to call stack limits).
1324 stack.set(object, other);
1325 var result = equalArrays(convert(object), convert(other), equalFunc, customizer, bitmask, stack);
1326 stack['delete'](object);
1327 return result;
1328
1329 case symbolTag:
1330 if (symbolValueOf) {
1331 return symbolValueOf.call(object) == symbolValueOf.call(other);
1332 }
1333 }
1334 return false;
1335}
1336
1337/**
1338 * A specialized version of `baseIsEqualDeep` for objects with support for
1339 * partial deep comparisons.
1340 *
1341 * @private
1342 * @param {Object} object The object to compare.
1343 * @param {Object} other The other object to compare.
1344 * @param {Function} equalFunc The function to determine equivalents of values.
1345 * @param {Function} customizer The function to customize comparisons.
1346 * @param {number} bitmask The bitmask of comparison flags. See `baseIsEqual`
1347 * for more details.
1348 * @param {Object} stack Tracks traversed `object` and `other` objects.
1349 * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
1350 */
1351function equalObjects(object, other, equalFunc, customizer, bitmask, stack) {
1352 var isPartial = bitmask & PARTIAL_COMPARE_FLAG,
1353 objProps = keys(object),
1354 objLength = objProps.length,
1355 othProps = keys(other),
1356 othLength = othProps.length;
1357
1358 if (objLength != othLength && !isPartial) {
1359 return false;
1360 }
1361 var index = objLength;
1362 while (index--) {
1363 var key = objProps[index];
1364 if (!(isPartial ? key in other : baseHas(other, key))) {
1365 return false;
1366 }
1367 }
1368 // Assume cyclic values are equal.
1369 var stacked = stack.get(object);
1370 if (stacked && stack.get(other)) {
1371 return stacked == other;
1372 }
1373 var result = true;
1374 stack.set(object, other);
1375 stack.set(other, object);
1376
1377 var skipCtor = isPartial;
1378 while (++index < objLength) {
1379 key = objProps[index];
1380 var objValue = object[key],
1381 othValue = other[key];
1382
1383 if (customizer) {
1384 var compared = isPartial
1385 ? customizer(othValue, objValue, key, other, object, stack)
1386 : customizer(objValue, othValue, key, object, other, stack);
1387 }
1388 // Recursively compare objects (susceptible to call stack limits).
1389 if (!(compared === undefined
1390 ? (objValue === othValue || equalFunc(objValue, othValue, customizer, bitmask, stack))
1391 : compared
1392 )) {
1393 result = false;
1394 break;
1395 }
1396 skipCtor || (skipCtor = key == 'constructor');
1397 }
1398 if (result && !skipCtor) {
1399 var objCtor = object.constructor,
1400 othCtor = other.constructor;
1401
1402 // Non `Object` object instances with different constructors are not equal.
1403 if (objCtor != othCtor &&
1404 ('constructor' in object && 'constructor' in other) &&
1405 !(typeof objCtor == 'function' && objCtor instanceof objCtor &&
1406 typeof othCtor == 'function' && othCtor instanceof othCtor)) {
1407 result = false;
1408 }
1409 }
1410 stack['delete'](object);
1411 stack['delete'](other);
1412 return result;
1413}
1414
1415/**
1416 * Gets the "length" property value of `object`.
1417 *
1418 * **Note:** This function is used to avoid a
1419 * [JIT bug](https://bugs.webkit.org/show_bug.cgi?id=142792) that affects
1420 * Safari on at least iOS 8.1-8.3 ARM64.
1421 *
1422 * @private
1423 * @param {Object} object The object to query.
1424 * @returns {*} Returns the "length" value.
1425 */
1426var getLength = baseProperty('length');
1427
1428/**
1429 * Gets the data for `map`.
1430 *
1431 * @private
1432 * @param {Object} map The map to query.
1433 * @param {string} key The reference key.
1434 * @returns {*} Returns the map data.
1435 */
1436function getMapData(map, key) {
1437 var data = map.__data__;
1438 return isKeyable(key)
1439 ? data[typeof key == 'string' ? 'string' : 'hash']
1440 : data.map;
1441}
1442
1443/**
1444 * Gets the property names, values, and compare flags of `object`.
1445 *
1446 * @private
1447 * @param {Object} object The object to query.
1448 * @returns {Array} Returns the match data of `object`.
1449 */
1450function getMatchData(object) {
1451 var result = keys(object),
1452 length = result.length;
1453
1454 while (length--) {
1455 var key = result[length],
1456 value = object[key];
1457
1458 result[length] = [key, value, isStrictComparable(value)];
1459 }
1460 return result;
1461}
1462
1463/**
1464 * Gets the native function at `key` of `object`.
1465 *
1466 * @private
1467 * @param {Object} object The object to query.
1468 * @param {string} key The key of the method to get.
1469 * @returns {*} Returns the function if it's native, else `undefined`.
1470 */
1471function getNative(object, key) {
1472 var value = getValue(object, key);
1473 return baseIsNative(value) ? value : undefined;
1474}
1475
1476/**
1477 * Gets the `[[Prototype]]` of `value`.
1478 *
1479 * @private
1480 * @param {*} value The value to query.
1481 * @returns {null|Object} Returns the `[[Prototype]]`.
1482 */
1483var getPrototype = overArg(nativeGetPrototype, Object);
1484
1485/**
1486 * Gets the `toStringTag` of `value`.
1487 *
1488 * @private
1489 * @param {*} value The value to query.
1490 * @returns {string} Returns the `toStringTag`.
1491 */
1492var getTag = baseGetTag;
1493
1494// Fallback for data views, maps, sets, and weak maps in IE 11,
1495// for data views in Edge, and promises in Node.js.
1496if ((DataView && getTag(new DataView(new ArrayBuffer(1))) != dataViewTag) ||
1497 (Map && getTag(new Map) != mapTag) ||
1498 (Promise && getTag(Promise.resolve()) != promiseTag) ||
1499 (Set && getTag(new Set) != setTag) ||
1500 (WeakMap && getTag(new WeakMap) != weakMapTag)) {
1501 getTag = function(value) {
1502 var result = objectToString.call(value),
1503 Ctor = result == objectTag ? value.constructor : undefined,
1504 ctorString = Ctor ? toSource(Ctor) : undefined;
1505
1506 if (ctorString) {
1507 switch (ctorString) {
1508 case dataViewCtorString: return dataViewTag;
1509 case mapCtorString: return mapTag;
1510 case promiseCtorString: return promiseTag;
1511 case setCtorString: return setTag;
1512 case weakMapCtorString: return weakMapTag;
1513 }
1514 }
1515 return result;
1516 };
1517}
1518
1519/**
1520 * Checks if `path` exists on `object`.
1521 *
1522 * @private
1523 * @param {Object} object The object to query.
1524 * @param {Array|string} path The path to check.
1525 * @param {Function} hasFunc The function to check properties.
1526 * @returns {boolean} Returns `true` if `path` exists, else `false`.
1527 */
1528function hasPath(object, path, hasFunc) {
1529 path = isKey(path, object) ? [path] : castPath(path);
1530
1531 var result,
1532 index = -1,
1533 length = path.length;
1534
1535 while (++index < length) {
1536 var key = toKey(path[index]);
1537 if (!(result = object != null && hasFunc(object, key))) {
1538 break;
1539 }
1540 object = object[key];
1541 }
1542 if (result) {
1543 return result;
1544 }
1545 var length = object ? object.length : 0;
1546 return !!length && isLength(length) && isIndex(key, length) &&
1547 (isArray(object) || isString(object) || isArguments(object));
1548}
1549
1550/**
1551 * Creates an array of index keys for `object` values of arrays,
1552 * `arguments` objects, and strings, otherwise `null` is returned.
1553 *
1554 * @private
1555 * @param {Object} object The object to query.
1556 * @returns {Array|null} Returns index keys, else `null`.
1557 */
1558function indexKeys(object) {
1559 var length = object ? object.length : undefined;
1560 if (isLength(length) &&
1561 (isArray(object) || isString(object) || isArguments(object))) {
1562 return baseTimes(length, String);
1563 }
1564 return null;
1565}
1566
1567/**
1568 * Checks if `value` is a valid array-like index.
1569 *
1570 * @private
1571 * @param {*} value The value to check.
1572 * @param {number} [length=MAX_SAFE_INTEGER] The upper bounds of a valid index.
1573 * @returns {boolean} Returns `true` if `value` is a valid index, else `false`.
1574 */
1575function isIndex(value, length) {
1576 length = length == null ? MAX_SAFE_INTEGER : length;
1577 return !!length &&
1578 (typeof value == 'number' || reIsUint.test(value)) &&
1579 (value > -1 && value % 1 == 0 && value < length);
1580}
1581
1582/**
1583 * Checks if `value` is a property name and not a property path.
1584 *
1585 * @private
1586 * @param {*} value The value to check.
1587 * @param {Object} [object] The object to query keys on.
1588 * @returns {boolean} Returns `true` if `value` is a property name, else `false`.
1589 */
1590function isKey(value, object) {
1591 if (isArray(value)) {
1592 return false;
1593 }
1594 var type = typeof value;
1595 if (type == 'number' || type == 'symbol' || type == 'boolean' ||
1596 value == null || isSymbol(value)) {
1597 return true;
1598 }
1599 return reIsPlainProp.test(value) || !reIsDeepProp.test(value) ||
1600 (object != null && value in Object(object));
1601}
1602
1603/**
1604 * Checks if `value` is suitable for use as unique object key.
1605 *
1606 * @private
1607 * @param {*} value The value to check.
1608 * @returns {boolean} Returns `true` if `value` is suitable, else `false`.
1609 */
1610function isKeyable(value) {
1611 var type = typeof value;
1612 return (type == 'string' || type == 'number' || type == 'symbol' || type == 'boolean')
1613 ? (value !== '__proto__')
1614 : (value === null);
1615}
1616
1617/**
1618 * Checks if `func` has its source masked.
1619 *
1620 * @private
1621 * @param {Function} func The function to check.
1622 * @returns {boolean} Returns `true` if `func` is masked, else `false`.
1623 */
1624function isMasked(func) {
1625 return !!maskSrcKey && (maskSrcKey in func);
1626}
1627
1628/**
1629 * Checks if `value` is likely a prototype object.
1630 *
1631 * @private
1632 * @param {*} value The value to check.
1633 * @returns {boolean} Returns `true` if `value` is a prototype, else `false`.
1634 */
1635function isPrototype(value) {
1636 var Ctor = value && value.constructor,
1637 proto = (typeof Ctor == 'function' && Ctor.prototype) || objectProto;
1638
1639 return value === proto;
1640}
1641
1642/**
1643 * Checks if `value` is suitable for strict equality comparisons, i.e. `===`.
1644 *
1645 * @private
1646 * @param {*} value The value to check.
1647 * @returns {boolean} Returns `true` if `value` if suitable for strict
1648 * equality comparisons, else `false`.
1649 */
1650function isStrictComparable(value) {
1651 return value === value && !isObject(value);
1652}
1653
1654/**
1655 * A specialized version of `matchesProperty` for source values suitable
1656 * for strict equality comparisons, i.e. `===`.
1657 *
1658 * @private
1659 * @param {string} key The key of the property to get.
1660 * @param {*} srcValue The value to match.
1661 * @returns {Function} Returns the new spec function.
1662 */
1663function matchesStrictComparable(key, srcValue) {
1664 return function(object) {
1665 if (object == null) {
1666 return false;
1667 }
1668 return object[key] === srcValue &&
1669 (srcValue !== undefined || (key in Object(object)));
1670 };
1671}
1672
1673/**
1674 * Converts `string` to a property path array.
1675 *
1676 * @private
1677 * @param {string} string The string to convert.
1678 * @returns {Array} Returns the property path array.
1679 */
1680var stringToPath = memoize(function(string) {
1681 string = toString(string);
1682
1683 var result = [];
1684 if (reLeadingDot.test(string)) {
1685 result.push('');
1686 }
1687 string.replace(rePropName, function(match, number, quote, string) {
1688 result.push(quote ? string.replace(reEscapeChar, '$1') : (number || match));
1689 });
1690 return result;
1691});
1692
1693/**
1694 * Converts `value` to a string key if it's not a string or symbol.
1695 *
1696 * @private
1697 * @param {*} value The value to inspect.
1698 * @returns {string|symbol} Returns the key.
1699 */
1700function toKey(value) {
1701 if (typeof value == 'string' || isSymbol(value)) {
1702 return value;
1703 }
1704 var result = (value + '');
1705 return (result == '0' && (1 / value) == -INFINITY) ? '-0' : result;
1706}
1707
1708/**
1709 * Converts `func` to its source code.
1710 *
1711 * @private
1712 * @param {Function} func The function to process.
1713 * @returns {string} Returns the source code.
1714 */
1715function toSource(func) {
1716 if (func != null) {
1717 try {
1718 return funcToString.call(func);
1719 } catch (e) {}
1720 try {
1721 return (func + '');
1722 } catch (e) {}
1723 }
1724 return '';
1725}
1726
1727/**
1728 * Creates a function that memoizes the result of `func`. If `resolver` is
1729 * provided, it determines the cache key for storing the result based on the
1730 * arguments provided to the memoized function. By default, the first argument
1731 * provided to the memoized function is used as the map cache key. The `func`
1732 * is invoked with the `this` binding of the memoized function.
1733 *
1734 * **Note:** The cache is exposed as the `cache` property on the memoized
1735 * function. Its creation may be customized by replacing the `_.memoize.Cache`
1736 * constructor with one whose instances implement the
1737 * [`Map`](http://ecma-international.org/ecma-262/6.0/#sec-properties-of-the-map-prototype-object)
1738 * method interface of `delete`, `get`, `has`, and `set`.
1739 *
1740 * @static
1741 * @memberOf _
1742 * @since 0.1.0
1743 * @category Function
1744 * @param {Function} func The function to have its output memoized.
1745 * @param {Function} [resolver] The function to resolve the cache key.
1746 * @returns {Function} Returns the new memoized function.
1747 * @example
1748 *
1749 * var object = { 'a': 1, 'b': 2 };
1750 * var other = { 'c': 3, 'd': 4 };
1751 *
1752 * var values = _.memoize(_.values);
1753 * values(object);
1754 * // => [1, 2]
1755 *
1756 * values(other);
1757 * // => [3, 4]
1758 *
1759 * object.a = 2;
1760 * values(object);
1761 * // => [1, 2]
1762 *
1763 * // Modify the result cache.
1764 * values.cache.set(object, ['a', 'b']);
1765 * values(object);
1766 * // => ['a', 'b']
1767 *
1768 * // Replace `_.memoize.Cache`.
1769 * _.memoize.Cache = WeakMap;
1770 */
1771function memoize(func, resolver) {
1772 if (typeof func != 'function' || (resolver && typeof resolver != 'function')) {
1773 throw new TypeError(FUNC_ERROR_TEXT);
1774 }
1775 var memoized = function() {
1776 var args = arguments,
1777 key = resolver ? resolver.apply(this, args) : args[0],
1778 cache = memoized.cache;
1779
1780 if (cache.has(key)) {
1781 return cache.get(key);
1782 }
1783 var result = func.apply(this, args);
1784 memoized.cache = cache.set(key, result);
1785 return result;
1786 };
1787 memoized.cache = new (memoize.Cache || MapCache);
1788 return memoized;
1789}
1790
1791// Assign cache to `_.memoize`.
1792memoize.Cache = MapCache;
1793
1794/**
1795 * Performs a
1796 * [`SameValueZero`](http://ecma-international.org/ecma-262/6.0/#sec-samevaluezero)
1797 * comparison between two values to determine if they are equivalent.
1798 *
1799 * @static
1800 * @memberOf _
1801 * @since 4.0.0
1802 * @category Lang
1803 * @param {*} value The value to compare.
1804 * @param {*} other The other value to compare.
1805 * @returns {boolean} Returns `true` if the values are equivalent, else `false`.
1806 * @example
1807 *
1808 * var object = { 'a': 1 };
1809 * var other = { 'a': 1 };
1810 *
1811 * _.eq(object, object);
1812 * // => true
1813 *
1814 * _.eq(object, other);
1815 * // => false
1816 *
1817 * _.eq('a', 'a');
1818 * // => true
1819 *
1820 * _.eq('a', Object('a'));
1821 * // => false
1822 *
1823 * _.eq(NaN, NaN);
1824 * // => true
1825 */
1826function eq(value, other) {
1827 return value === other || (value !== value && other !== other);
1828}
1829
1830/**
1831 * Checks if `value` is likely an `arguments` object.
1832 *
1833 * @static
1834 * @memberOf _
1835 * @since 0.1.0
1836 * @category Lang
1837 * @param {*} value The value to check.
1838 * @returns {boolean} Returns `true` if `value` is an `arguments` object,
1839 * else `false`.
1840 * @example
1841 *
1842 * _.isArguments(function() { return arguments; }());
1843 * // => true
1844 *
1845 * _.isArguments([1, 2, 3]);
1846 * // => false
1847 */
1848function isArguments(value) {
1849 // Safari 8.1 incorrectly makes `arguments.callee` enumerable in strict mode.
1850 return isArrayLikeObject(value) && hasOwnProperty.call(value, 'callee') &&
1851 (!propertyIsEnumerable.call(value, 'callee') || objectToString.call(value) == argsTag);
1852}
1853
1854/**
1855 * Checks if `value` is classified as an `Array` object.
1856 *
1857 * @static
1858 * @memberOf _
1859 * @since 0.1.0
1860 * @category Lang
1861 * @param {*} value The value to check.
1862 * @returns {boolean} Returns `true` if `value` is an array, else `false`.
1863 * @example
1864 *
1865 * _.isArray([1, 2, 3]);
1866 * // => true
1867 *
1868 * _.isArray(document.body.children);
1869 * // => false
1870 *
1871 * _.isArray('abc');
1872 * // => false
1873 *
1874 * _.isArray(_.noop);
1875 * // => false
1876 */
1877var isArray = Array.isArray;
1878
1879/**
1880 * Checks if `value` is array-like. A value is considered array-like if it's
1881 * not a function and has a `value.length` that's an integer greater than or
1882 * equal to `0` and less than or equal to `Number.MAX_SAFE_INTEGER`.
1883 *
1884 * @static
1885 * @memberOf _
1886 * @since 4.0.0
1887 * @category Lang
1888 * @param {*} value The value to check.
1889 * @returns {boolean} Returns `true` if `value` is array-like, else `false`.
1890 * @example
1891 *
1892 * _.isArrayLike([1, 2, 3]);
1893 * // => true
1894 *
1895 * _.isArrayLike(document.body.children);
1896 * // => true
1897 *
1898 * _.isArrayLike('abc');
1899 * // => true
1900 *
1901 * _.isArrayLike(_.noop);
1902 * // => false
1903 */
1904function isArrayLike(value) {
1905 return value != null && isLength(getLength(value)) && !isFunction(value);
1906}
1907
1908/**
1909 * This method is like `_.isArrayLike` except that it also checks if `value`
1910 * is an object.
1911 *
1912 * @static
1913 * @memberOf _
1914 * @since 4.0.0
1915 * @category Lang
1916 * @param {*} value The value to check.
1917 * @returns {boolean} Returns `true` if `value` is an array-like object,
1918 * else `false`.
1919 * @example
1920 *
1921 * _.isArrayLikeObject([1, 2, 3]);
1922 * // => true
1923 *
1924 * _.isArrayLikeObject(document.body.children);
1925 * // => true
1926 *
1927 * _.isArrayLikeObject('abc');
1928 * // => false
1929 *
1930 * _.isArrayLikeObject(_.noop);
1931 * // => false
1932 */
1933function isArrayLikeObject(value) {
1934 return isObjectLike(value) && isArrayLike(value);
1935}
1936
1937/**
1938 * Checks if `value` is classified as a `Function` object.
1939 *
1940 * @static
1941 * @memberOf _
1942 * @since 0.1.0
1943 * @category Lang
1944 * @param {*} value The value to check.
1945 * @returns {boolean} Returns `true` if `value` is a function, else `false`.
1946 * @example
1947 *
1948 * _.isFunction(_);
1949 * // => true
1950 *
1951 * _.isFunction(/abc/);
1952 * // => false
1953 */
1954function isFunction(value) {
1955 // The use of `Object#toString` avoids issues with the `typeof` operator
1956 // in Safari 8 which returns 'object' for typed array and weak map constructors,
1957 // and PhantomJS 1.9 which returns 'function' for `NodeList` instances.
1958 var tag = isObject(value) ? objectToString.call(value) : '';
1959 return tag == funcTag || tag == genTag;
1960}
1961
1962/**
1963 * Checks if `value` is a valid array-like length.
1964 *
1965 * **Note:** This function is loosely based on
1966 * [`ToLength`](http://ecma-international.org/ecma-262/6.0/#sec-tolength).
1967 *
1968 * @static
1969 * @memberOf _
1970 * @since 4.0.0
1971 * @category Lang
1972 * @param {*} value The value to check.
1973 * @returns {boolean} Returns `true` if `value` is a valid length,
1974 * else `false`.
1975 * @example
1976 *
1977 * _.isLength(3);
1978 * // => true
1979 *
1980 * _.isLength(Number.MIN_VALUE);
1981 * // => false
1982 *
1983 * _.isLength(Infinity);
1984 * // => false
1985 *
1986 * _.isLength('3');
1987 * // => false
1988 */
1989function isLength(value) {
1990 return typeof value == 'number' &&
1991 value > -1 && value % 1 == 0 && value <= MAX_SAFE_INTEGER;
1992}
1993
1994/**
1995 * Checks if `value` is the
1996 * [language type](http://www.ecma-international.org/ecma-262/6.0/#sec-ecmascript-language-types)
1997 * of `Object`. (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)
1998 *
1999 * @static
2000 * @memberOf _
2001 * @since 0.1.0
2002 * @category Lang
2003 * @param {*} value The value to check.
2004 * @returns {boolean} Returns `true` if `value` is an object, else `false`.
2005 * @example
2006 *
2007 * _.isObject({});
2008 * // => true
2009 *
2010 * _.isObject([1, 2, 3]);
2011 * // => true
2012 *
2013 * _.isObject(_.noop);
2014 * // => true
2015 *
2016 * _.isObject(null);
2017 * // => false
2018 */
2019function isObject(value) {
2020 var type = typeof value;
2021 return !!value && (type == 'object' || type == 'function');
2022}
2023
2024/**
2025 * Checks if `value` is object-like. A value is object-like if it's not `null`
2026 * and has a `typeof` result of "object".
2027 *
2028 * @static
2029 * @memberOf _
2030 * @since 4.0.0
2031 * @category Lang
2032 * @param {*} value The value to check.
2033 * @returns {boolean} Returns `true` if `value` is object-like, else `false`.
2034 * @example
2035 *
2036 * _.isObjectLike({});
2037 * // => true
2038 *
2039 * _.isObjectLike([1, 2, 3]);
2040 * // => true
2041 *
2042 * _.isObjectLike(_.noop);
2043 * // => false
2044 *
2045 * _.isObjectLike(null);
2046 * // => false
2047 */
2048function isObjectLike(value) {
2049 return !!value && typeof value == 'object';
2050}
2051
2052/**
2053 * Checks if `value` is classified as a `String` primitive or object.
2054 *
2055 * @static
2056 * @since 0.1.0
2057 * @memberOf _
2058 * @category Lang
2059 * @param {*} value The value to check.
2060 * @returns {boolean} Returns `true` if `value` is a string, else `false`.
2061 * @example
2062 *
2063 * _.isString('abc');
2064 * // => true
2065 *
2066 * _.isString(1);
2067 * // => false
2068 */
2069function isString(value) {
2070 return typeof value == 'string' ||
2071 (!isArray(value) && isObjectLike(value) && objectToString.call(value) == stringTag);
2072}
2073
2074/**
2075 * Checks if `value` is classified as a `Symbol` primitive or object.
2076 *
2077 * @static
2078 * @memberOf _
2079 * @since 4.0.0
2080 * @category Lang
2081 * @param {*} value The value to check.
2082 * @returns {boolean} Returns `true` if `value` is a symbol, else `false`.
2083 * @example
2084 *
2085 * _.isSymbol(Symbol.iterator);
2086 * // => true
2087 *
2088 * _.isSymbol('abc');
2089 * // => false
2090 */
2091function isSymbol(value) {
2092 return typeof value == 'symbol' ||
2093 (isObjectLike(value) && objectToString.call(value) == symbolTag);
2094}
2095
2096/**
2097 * Checks if `value` is classified as a typed array.
2098 *
2099 * @static
2100 * @memberOf _
2101 * @since 3.0.0
2102 * @category Lang
2103 * @param {*} value The value to check.
2104 * @returns {boolean} Returns `true` if `value` is a typed array, else `false`.
2105 * @example
2106 *
2107 * _.isTypedArray(new Uint8Array);
2108 * // => true
2109 *
2110 * _.isTypedArray([]);
2111 * // => false
2112 */
2113var isTypedArray = nodeIsTypedArray ? baseUnary(nodeIsTypedArray) : baseIsTypedArray;
2114
2115/**
2116 * Converts `value` to a string. An empty string is returned for `null`
2117 * and `undefined` values. The sign of `-0` is preserved.
2118 *
2119 * @static
2120 * @memberOf _
2121 * @since 4.0.0
2122 * @category Lang
2123 * @param {*} value The value to process.
2124 * @returns {string} Returns the string.
2125 * @example
2126 *
2127 * _.toString(null);
2128 * // => ''
2129 *
2130 * _.toString(-0);
2131 * // => '-0'
2132 *
2133 * _.toString([1, 2, 3]);
2134 * // => '1,2,3'
2135 */
2136function toString(value) {
2137 return value == null ? '' : baseToString(value);
2138}
2139
2140/**
2141 * Gets the value at `path` of `object`. If the resolved value is
2142 * `undefined`, the `defaultValue` is returned in its place.
2143 *
2144 * @static
2145 * @memberOf _
2146 * @since 3.7.0
2147 * @category Object
2148 * @param {Object} object The object to query.
2149 * @param {Array|string} path The path of the property to get.
2150 * @param {*} [defaultValue] The value returned for `undefined` resolved values.
2151 * @returns {*} Returns the resolved value.
2152 * @example
2153 *
2154 * var object = { 'a': [{ 'b': { 'c': 3 } }] };
2155 *
2156 * _.get(object, 'a[0].b.c');
2157 * // => 3
2158 *
2159 * _.get(object, ['a', '0', 'b', 'c']);
2160 * // => 3
2161 *
2162 * _.get(object, 'a.b.c', 'default');
2163 * // => 'default'
2164 */
2165function get(object, path, defaultValue) {
2166 var result = object == null ? undefined : baseGet(object, path);
2167 return result === undefined ? defaultValue : result;
2168}
2169
2170/**
2171 * Checks if `path` is a direct or inherited property of `object`.
2172 *
2173 * @static
2174 * @memberOf _
2175 * @since 4.0.0
2176 * @category Object
2177 * @param {Object} object The object to query.
2178 * @param {Array|string} path The path to check.
2179 * @returns {boolean} Returns `true` if `path` exists, else `false`.
2180 * @example
2181 *
2182 * var object = _.create({ 'a': _.create({ 'b': 2 }) });
2183 *
2184 * _.hasIn(object, 'a');
2185 * // => true
2186 *
2187 * _.hasIn(object, 'a.b');
2188 * // => true
2189 *
2190 * _.hasIn(object, ['a', 'b']);
2191 * // => true
2192 *
2193 * _.hasIn(object, 'b');
2194 * // => false
2195 */
2196function hasIn(object, path) {
2197 return object != null && hasPath(object, path, baseHasIn);
2198}
2199
2200/**
2201 * Creates an array of the own enumerable property names of `object`.
2202 *
2203 * **Note:** Non-object values are coerced to objects. See the
2204 * [ES spec](http://ecma-international.org/ecma-262/6.0/#sec-object.keys)
2205 * for more details.
2206 *
2207 * @static
2208 * @since 0.1.0
2209 * @memberOf _
2210 * @category Object
2211 * @param {Object} object The object to query.
2212 * @returns {Array} Returns the array of property names.
2213 * @example
2214 *
2215 * function Foo() {
2216 * this.a = 1;
2217 * this.b = 2;
2218 * }
2219 *
2220 * Foo.prototype.c = 3;
2221 *
2222 * _.keys(new Foo);
2223 * // => ['a', 'b'] (iteration order is not guaranteed)
2224 *
2225 * _.keys('hi');
2226 * // => ['0', '1']
2227 */
2228function keys(object) {
2229 var isProto = isPrototype(object);
2230 if (!(isProto || isArrayLike(object))) {
2231 return baseKeys(object);
2232 }
2233 var indexes = indexKeys(object),
2234 skipIndexes = !!indexes,
2235 result = indexes || [],
2236 length = result.length;
2237
2238 for (var key in object) {
2239 if (baseHas(object, key) &&
2240 !(skipIndexes && (key == 'length' || isIndex(key, length))) &&
2241 !(isProto && key == 'constructor')) {
2242 result.push(key);
2243 }
2244 }
2245 return result;
2246}
2247
2248/**
2249 * This method returns the first argument it receives.
2250 *
2251 * @static
2252 * @since 0.1.0
2253 * @memberOf _
2254 * @category Util
2255 * @param {*} value Any value.
2256 * @returns {*} Returns `value`.
2257 * @example
2258 *
2259 * var object = { 'a': 1 };
2260 *
2261 * console.log(_.identity(object) === object);
2262 * // => true
2263 */
2264function identity(value) {
2265 return value;
2266}
2267
2268/**
2269 * Creates a function that returns the value at `path` of a given object.
2270 *
2271 * @static
2272 * @memberOf _
2273 * @since 2.4.0
2274 * @category Util
2275 * @param {Array|string} path The path of the property to get.
2276 * @returns {Function} Returns the new accessor function.
2277 * @example
2278 *
2279 * var objects = [
2280 * { 'a': { 'b': 2 } },
2281 * { 'a': { 'b': 1 } }
2282 * ];
2283 *
2284 * _.map(objects, _.property('a.b'));
2285 * // => [2, 1]
2286 *
2287 * _.map(_.sortBy(objects, _.property(['a', 'b'])), 'a.b');
2288 * // => [1, 2]
2289 */
2290function property(path) {
2291 return isKey(path) ? baseProperty(toKey(path)) : basePropertyDeep(path);
2292}
2293
2294/**
2295 * This method is like `_.min` except that it accepts `iteratee` which is
2296 * invoked for each element in `array` to generate the criterion by which
2297 * the value is ranked. The iteratee is invoked with one argument: (value).
2298 *
2299 * @static
2300 * @memberOf _
2301 * @since 4.0.0
2302 * @category Math
2303 * @param {Array} array The array to iterate over.
2304 * @param {Function} [iteratee=_.identity] The iteratee invoked per element.
2305 * @returns {*} Returns the minimum value.
2306 * @example
2307 *
2308 * var objects = [{ 'n': 1 }, { 'n': 2 }];
2309 *
2310 * _.minBy(objects, function(o) { return o.n; });
2311 * // => { 'n': 1 }
2312 *
2313 * // The `_.property` iteratee shorthand.
2314 * _.minBy(objects, 'n');
2315 * // => { 'n': 1 }
2316 */
2317function minBy(array, iteratee) {
2318 return (array && array.length)
2319 ? baseExtremum(array, baseIteratee(iteratee, 2), baseLt)
2320 : undefined;
2321}
2322
2323module.exports = minBy;