[英]Compare Object Arrays. Return matching Object keys & values
OBJECTIVE 目的
Make a function that looks through a list (collection) and returns an array of all objects that have equivalent property values (source). 创建一个通过列表(集合)查找并返回具有相等属性值的所有对象(源)的数组的函数。
EXAMPLE #1 示例#1
function where(collection, source) {
var arr = [];
return arr;
}
where([
{ first: 'Romeo', last: 'Montague' },
{ first: 'Mercutio', last: null },
{ first: 'Tybalt', last: 'Capulet' }],
{ last: 'Capulet' });
EXPECTED OUTPUT #1 预期输出#1
[{ first: 'Tybalt', last: 'Capulet' }]
EXAMPLE #2 例子#2
where(
[{ 'a': 1 },
{ 'a': 1 },
{ 'a': 1, 'b': 2 }],
{ 'a': 1 }),
EXPECTED OUTPUT #2 预期输出#2
[{ 'a': 1 }, { 'a': 1 }, { 'a': 1, 'b': 2 }]
QUESTIONS 质询
Since you can't use external libraries, here's a simple way to do what you need: 由于您不能使用外部库,因此这是一种执行所需操作的简单方法:
function where(collection, source) {
var keys = Object.keys(source);
return collection.filter(function (item) {
return keys.every(function (key) {
return source[key] == item[key];
});
});
}
-> Solution 1: Using Lodash Where
->解决方案1:
Where
Lodash Where
使用Where
For this kind of problems, you can use Lodash utility library. 对于此类问题,可以使用Lodash实用程序库。
Lodash already has where function which you need. Lodash已经具有您需要的where功能。
see the below example. 请参阅以下示例。
var out = _.where([{ first: 'Romeo', last: 'Montague' }, { first: 'Mercutio', last: null }, { first: 'Tybalt', last: 'Capulet' }], { last: 'Capulet' }); document.getElementById('out').innerHTML = JSON.stringify(out); var out2 = _.where( [{ 'a': 1 }, { 'a': 1 }, { 'a': 1, 'b': 2 }], { 'a': 1 }); document.getElementById('out2').innerHTML = JSON.stringify(out2);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/3.8.0/lodash.js"></script> <div id="out"></div> <hr/> <div id="out2"></div>
-> Solution 2: Custom Where
Implementation - >解决方案2:自定义
Where
执行
This implementation works with strings, single object , one level object and multilevel objects . 此实现适用于字符串,单个对象,一个一级对象和多个一级对象 。
function typeOf(o) {
return Object.prototype.toString.call(o).split(' ')[1].split(']')[0].toLowerCase();
}
function isUndefined(o) {
return typeOf(o) === 'undefined';
}
function where(collection, source) {
var checkArr = [];
if (typeOf(collection) === 'object') {
checkArr = [collection];
} else if (typeOf(collection) === 'array') {
checkArr = collection;
}
function isObjectSemiSame(obj, source, u) {
return Object.keys(source).every(function(key) {
if (isUndefined(obj) || isUndefined(obj[key])) {
return;
}
if (typeOf(source[key]) === 'object' || typeOf(source[key]) === 'array') {
return isObjectSemiSame(obj[key], source[key]);
}
return source[key] === obj[key];
});
}
return checkArr.filter(function(item) {
return isObjectSemiSame(item, source);
});
}
Jasmine tests for testing where
with strings, single object, one level object and multilevel objects. 茉莉测试用于测试
where
用字符串,单个对象,一个级别对象和多级的对象。
function typeOf(o) { return Object.prototype.toString.call(o).split(' ')[1].split(']')[0].toLowerCase(); } function isUndefined(o) { return typeOf(o) === 'undefined'; } function where(collection, source) { var checkArr = []; if (typeOf(collection) === 'object') { checkArr = [collection]; } else if (typeOf(collection) === 'array') { checkArr = collection; } function isObjectSemiSame(obj, source, u) { return Object.keys(source).every(function(key) { if (isUndefined(obj) || isUndefined(obj[key])) { return; } if (typeOf(source[key]) === 'object' || typeOf(source[key]) === 'array') { return isObjectSemiSame(obj[key], source[key]); } return source[key] === obj[key]; }); } return checkArr.filter(function(item) { return isObjectSemiSame(item, source); }); } describe('where method', function() { it('testing with strings', function() { var collection = [ "one", "two", "three" ]; var collection = [ "bamboo", "two", "bamboo", "link" ]; expect(where(collection, "two")).toEqual(["two"]); expect(where(collection, "bamboo")).toEqual(["bamboo", "bamboo"]); }); it('testing with one object', function() { var collection1 = { name: 'raju', age: 23, }; var collection2 = { name: 'Friko', age: 36, }; expect(where(collection1, { name: 'raju' })).toEqual([collection1]); expect(where(collection1, { name: 'Dump' })).toEqual([]); expect(where(collection2, { age: 36 })).toEqual([collection2]); expect(where(collection2, { car: 'audi' })).toEqual([]); }); it('testing with one level object', function() { var collection = [{ name: 'jack', age: 25 }, { name: 'missi', age: 23 }, { name: 'reddy', age: 46 }]; var source1 = { name: 'reddy' }; var source2 = { age: 25 }; expect(where(collection, source1)).toEqual([collection[2]]); expect(where(collection, source2)).toEqual([collection[0]]); }); it('testing with multilevel object', function() { var collection = [{ name: 'jack', age: 25, level1: { name: 'l1', level2: { name: 'l2', level3: { name: 'l3' } } } }, { name: 'missi', age: 23, level1: { name: 'l1' } }, { name: 'reddy', age: 46, feature: { flag: false } }]; var source1 = { level1: { name: 'l1' } }; var source2 = { level1: { name: 'l1', level2: { name: 'l2' } } }; var source3 = { feature: { flag: false } }; expect(where(collection, source1).length).toBe(2); expect(where(collection, source1)).toEqual(jasmine.arrayContaining([ collection[0], collection[1] ])); expect(where(collection, source2)).toEqual([collection[0]]); expect(where(collection, source3)).toEqual([collection[2]]); }); });
<script src="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/jasmine.min.js"></script> <link href="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/jasmine.min.css" rel="stylesheet" /> <script src="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/jasmine-html.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/boot.min.js"></script>
UPDATE: added custom where
implementation with jasmine tests 更新:添加了使用茉莉花测试实现的自定义
where
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.