jQuery 查找数组中具有最高属性值的对象索引
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/16509075/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Find index of object in array with highest value in property
提问by Rijstkoek
I've got an array with objects:
我有一个包含对象的数组:
var articles = [];
var article = {};
Simple loop that iterates x times {
article.text = "foobar";
article.color = "red";
article.number = 5;
articles.push(article);
}
I have no idea how many objects there will be in my array but they will all have different values for their properties, I just gave some examples here.
我不知道我的数组中有多少个对象,但它们的属性都有不同的值,我只是在这里举了一些例子。
Question
题
I need to find a way to go through all these objects and retrieve the index of the object that has the highest value in article.number. How can I achieve this? I may only use javascript, jQuery, etc.. no other languages.
我需要找到一种方法来遍历所有这些对象并检索在 article.number 中具有最高值的对象的索引。我怎样才能做到这一点?我可能只使用 javascript、jQuery 等。没有其他语言。
I'm guessing this will involve using both $.grep and Math.max but I'm stuck, I've never worked with $.grep before.
我猜这将涉及同时使用 $.grep 和 Math.max 但我被卡住了,我以前从未使用过 $.grep 。
In short:
简而言之:
var highestNumber = index of object where article.number is highest
回答by adeneo
There are many ways to do this, Math.max()
, $.grep
and $.map
being a few, but an easy and readable method that should be understandable is to just iterate the object, and check if the value is higher than a variable, if it is, set the variable to the higher number :
有很多方法可以做到这一点,Math.max()
,$.grep
和$.map
是少数,但一个简单易读的方法,应该是可以理解的是刚刚迭代的对象,并且,检查值大于变量更高,如果是,设置变量较高的数字:
var highest = 0;
$.each(articles, function(key, article) {
if (article.number > highest) highest = article.number;
});
// highest now contains the highest number
回答by ljfranklin
Underscore.jsis a wonderful library that provides functional operations for collections. A solution in underscore:
Underscore.js是一个很棒的库,它为集合提供函数式操作。下划线的解决方案:
var maxObj = _.max(array, function (obj) {
return obj.number;
});
var maxIndex = array.indexOf(maxObj);
While this example is fairly simple, the operations scale nicely. Say you wanted to sum the number property for each object in the array that had text equal to Foo
and color equal to red
:
虽然这个例子相当简单,但操作的伸缩性很好。假设您想对数组中文本等于Foo
且颜色等于 的每个对象的 number 属性求和red
:
var customSum = _.chain(array)
.where({
text: "Foo", color: "red"
})
.map(function(obj) {
return obj.number;
})
.reduce(function(memo, num) {
return memo + num;
}, 0)
.value();
If you're at all concerned with performance, an external library is certainly the way to go. There are a huge amount of optimizations that external libraries can provide that would be difficult to match in your own code. That said, when dealing with a small number of items (less than several thousand) there won't be an appreciable performance difference between any of the answers posted here. Don't sweat the benchmarking and use the answer that's the most understandable to you.
如果您完全关心性能,那么外部库肯定是您要走的路。外部库可以提供大量优化,这在您自己的代码中很难匹配。也就是说,在处理少量项目(少于几千个)时,此处发布的任何答案之间不会有明显的性能差异。不要为基准测试而烦恼,并使用您最容易理解的答案。
回答by georg
How about:
怎么样:
articleWithMaxNumber = articles.slice(0).sort(
function(x, y) { return y.number - x.number })[0]
and if you need an index:
如果您需要索引:
index = articles.indexOf(articleWithMaxNumber)
And for those thinking sorting might be an overkill to get the max value:
对于那些认为排序可能是获得最大值的过度杀伤力:
articleWithMaxNumber = articles.reduce(function(max, x) {
return x.number > max.number ? x : max;
})
And here's a generic approach how to find a maximum of function applications using map-reduce:
这是如何使用 map-reduce 找到最大函数应用程序的通用方法:
function maxBy(array, fn) {
return array.map(function(x) {
return [x, fn(x)]
}).reduce(function(max, x) {
return x[1] > max[1] ? x : max;
})[0]
}
articleWithMaxNumber = maxBy(articles, function(x) { return x.number })
Some people raised concerns about the sort
method being "slow", compared to the iterative one. Here's a fiddlethat uses both methods to process an array with 50000 items. The sort
method is "slower" by about 50 millisecondson my machine. Depends on the application, but in most cases this is not something worth talking about.
sort
与迭代方法相比,有些人担心该方法“慢”。这是一个使用这两种方法处理具有50000 个项目的数组的小提琴。该方法在我的机器上“慢”了大约50 毫秒。取决于应用程序,但在大多数情况下,这不值得讨论。sort
var articles = [];
var len = 50000;
while (len--) {
var article = {};
article.text = "foobar";
article.color = "red";
article.number = Math.random();
articles.push(article);
}
d = performance.now();
max1 = articles.slice(0).sort(
function(x, y) {
return y.number - x.number
})[0]
time1 = performance.now() - d
d = performance.now();
max2 = articles.reduce(function(max, x) {
return x.number > max.number ? x : max;
})
time2 = performance.now() - d
document.body.innerHTML = [time1, time2].join("<br>")
回答by Xotic750
Here is one possible solution
这是一种可能的解决方案
Javascript
Javascript
var articles = [],
howMany = 5,
i = 0,
article,
highest;
while (i < howMany) {
article = {};
article.text = "foobar";
article.color = "red";
article.number = i;
articles.push(article);
i += 1;
}
console.log(articles);
hownMany = articles.length;
i = 0;
while (i < howMany) {
if (typeof highest !== "number" || articles[i].number > highest) {
highest = i;
}
i += 1;
}
console.log(articles[highest]);
On jsfiddle
Here is the performance testfor the current given methods, feel free to add answers.
这是当前给定方法的性能测试,请随时添加答案。
回答by kevin
items =>
items
.reduce(
( highest, item, index ) =>
item > highest.item
? { item, index }
: highest
, { item: Number.NEGATIVE_INFINITY }
)
.index
回答by Abdennour TOUMI
array[array.map((o)=>o.number).indexOf(Math.max(...array.map((o)=>o.number)))]
Means get element with index (i) where (i) is the index of highest number .
表示获取具有索引 (i) 的元素,其中 (i) 是最高数字的索引。
回答by Axel Amthor
I won't use anything like Math or jQuery, just sort the resulting array and popping off the last element:
我不会使用 Math 或 jQuery 之类的东西,只需对结果数组进行排序并弹出最后一个元素:
var sortArticles = function (a, b)
{
return ( a.number - b.number ); // should have some type checks ? inverse order: swap a/b
}
articles.sort(sortArticles);
highestArticle = articles.pop(); // or articles[array.length-1];
// take care if srticles.length = null !
As long as you don't have gazillions of articles in your memory, that's the fastest way.
只要您的记忆中没有海量文章,这就是最快的方法。