如何使用第二个数组中对象的相关属性对对象数组进行排序
how to sort an array of objects using a related property from objects in second array
关于使用JavaScript排序有很多问题,但我没有找到任何解决这种情况的方法,所以我不认为这是重复的。
我正在从一个api获取这样的数据:
//items array
var items = [{id:1, name:'bill'}, {id:2, name:'sam'}, {id:3, name: mary}, {id:4, name:'jane'}]
//sort order array
var order = [{id:1, sortindex:4}, {id:2, sortindex:2}, {id:3, sortindex: 1}, {id:4, sortindex:3}]
如何根据order数组中对象的sortindex
属性对items数组进行排序?这两个数组中的对象具有共同的属性id
。是否有优雅的lodash/underline解决方案?
使用lodash很简单。sortBy
函数会将项目移动到sortindex
位置,因此我们只需要使用find
来获取相应的对象,并返回其sortindex
属性供sortBy
使用。
var items = [{id:1, name:'bill'}, {id:2, name:'sam'}, {id:3, name: 'mary'}, {id:4, name:'jane'}];
var order = [{id:1, sortindex:4}, {id:2, sortindex:2}, {id:3, sortindex: 1}, {id:4, sortindex:3}];
var sorted = _.sortBy(items, function(item) {
// sorts by the value returned here
return _.find(order, function(ordItem) {
// find the object where the id's match
return item.id === ordItem.id;
}).sortindex; // that object's sortindex property is returned
});
document.body.textContent = JSON.stringify(sorted);
<script src="https://rawgit.com/lodash/lodash/3.0.1/lodash.min.js"></script>
如果您将订单存储为地图,那么使用香草Javascript就相当简单了。
var items = [{id:1, name:'bill'}, {id:2, name:'sam'}, {id:3, name: 'mary'}, {id:4, name:'jane'}];
var order = {1:4, 2:2, 3:1, 4:3};
items.sort(function (a, b) {
return (order[a.id] > order[b.id]) - (order[a.id] < order[b.id]);
});
或者,如果你坚持你的原始数据,假设它已经按照你显示的方式排序:
var items = [{id:1, name:'bill'}, {id:2, name:'sam'}, {id:3, name: 'mary'}, {id:4, name:'jane'}];
var order = [{id:1, sortindex:4}, {id:2, sortindex:2}, {id:3, sortindex: 1}, {id:4, sortindex:3}];
items.sort(function (a, b) {
var ai = order[a.id - 1].sortindex;
var bi = order[b.id - 1].sortindex;
return (ai > bi) - (ai < bi);
});
如果您不能假设数据已排序,请参阅此问题,例如如何根据数据创建地图。
请参阅演示:http://jsbin.com/qaquzi/1/edit?js,控制台
//items array
var items = [{id:1, name:'bill'}, {id:2, name:'sam'}, {id:3, name: 'mary'}, {id:4, name:'jane'}]
//sort order array
var order = [{id:1, sortindex:4}, {id:2, sortindex:2}, {id:3, sortindex: 1}, {id:4, sortindex:3}]
var sortedOrder = _.sortBy(order, 'sortindex');
var bb = _.map(sortedOrder, function (i) {
return i.id;
})
var sorted = [];
for (var i = 0, ii = bb.length; i < ii; i++) {
for (var m = 0, mm = items.length; m < mm; m++) {
var a = items[m];
if (a.id == bb[i]) {
sorted.push(items[m]);
}
}
}
console.log(sorted);
这是我的解决方案:
var items = [
{ id: 1, name: 'bill' },
{ id: 2, name: 'sam' },
{ id: 3, name: 'mary' },
{ id: 4, name: 'jane' }
];
var order = [
{ id: 1, sortindex: 4 },
{ id: 2, sortindex: 2 },
{ id: 3, sortindex: 1 },
{ id: 4, sortindex: 3 }
];
_(items)
.indexBy('id')
.at(_.pluck(_.sortBy(order, 'sortindex'), 'id'))
.pluck('name')
.value();
// → [ 'mary', 'sam', 'jane', 'bill' ]
以下是发生的事情:
- indexBy()函数将
items
转换为一个对象,其中id
值是键 - at()函数从对象中获取值,按的顺序传入键
- 函数的作用是通过
sortindex
键对order
进行排序 - 函数的作用是:获取已排序的
id
数组
这是我的解决方案。如果您知道两个数组在id的长度和位置上都匹配,那么这是一个简洁的解决方案:
_.chain(items)
.merge(order)
.sortBy('sortindex')
.map(_.partialRight(_.omit, 'sortindex'))
.value()
否则,如果不能保证对它们进行排序,则可以使用map/find/merge来解析这些项。
_.chain(items)
.map(function(item) {
return _.merge(item, _.find(order, {'id': item.id}));
})
.sortBy('sortindex')
.map(_.partialRight(_.omit, 'sortindex'))
.value()
相关文章:
- Javascript(Angular)从一个对象数组到第二个数组查找值
- 在Javascript中转换对象数组
- 在JavaScript中通过索引从对象数组中获取值
- Backbone虹吸以获取对象数组
- 如何在DataTables 2.1中迭代对象数组
- Javascript-根据赋值顺序,按键合并对象数组
- 将事件附加到对象/数组
- jQuery$.inArray()总是返回-1和一个对象数组
- javascript处理一个对象数组以获得一个新的对象数组
- javascript在数组中获取对象数组中键的所有不同值
- 在对象数组中查找多个值的d3范围
- Undercore.js获取对象数组中键对象的值
- 在mongoose中使用正则表达式在对象数组中进行查询搜索
- 如何通过json对象数组为嵌套对象赋值
- 如何循环通过2个对象数组并通过匹配id进行合并
- 为对象数组创建列表项
- 如何使用javascript合并两个对象数组
- JSON到对象数组,并向每个对象添加项
- JavaScript:从对象数组中获取唯一值及其计数
- 按不同项目对对象数组进行排序