/*! * make-iterator * * Copyright (c) 2014-2018, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; var typeOf = require('kind-of'); module.exports = function makeIterator(target, thisArg) { switch (typeOf(target)) { case 'undefined': case 'null': return noop; case 'function': // function is the first to improve perf (most common case) // also avoid using `Function#call` if not needed, which boosts // perf a lot in some cases return (typeof thisArg !== 'undefined') ? function(val, i, arr) { return target.call(thisArg, val, i, arr); } : target; case 'object': return function(val) { return deepMatches(val, target); }; case 'regexp': return function(str) { return target.test(str); }; case 'string': case 'number': default: { return prop(target); } } }; function containsMatch(array, value) { var len = array.length; var i = -1; while (++i < len) { if (deepMatches(array[i], value)) { return true; } } return false; } function matchArray(arr, value) { var len = value.length; var i = -1; while (++i < len) { if (!containsMatch(arr, value[i])) { return false; } } return true; } function matchObject(obj, value) { for (var key in value) { if (value.hasOwnProperty(key)) { if (deepMatches(obj[key], value[key]) === false) { return false; } } } return true; } /** * Recursively compare objects */ function deepMatches(val, value) { if (typeOf(val) === 'object') { if (Array.isArray(val) && Array.isArray(value)) { return matchArray(val, value); } else { return matchObject(val, value); } } else { return val === value; } } function prop(name) { return function(obj) { return obj[name]; }; } function noop(val) { return val; }