返回数组中最大值的索引

我有这个:

var arr = [0, 21, 22, 7];

将最高值的索引返回到另一个变量的最佳方法是什么?

208123 次浏览

这可能是最好的方法,因为它是可靠的,可以在老的浏览器上工作:

function indexOfMax(arr) {
if (arr.length === 0) {
return -1;
}


var max = arr[0];
var maxIndex = 0;


for (var i = 1; i < arr.length; i++) {
if (arr[i] > max) {
maxIndex = i;
max = arr[i];
}
}


return maxIndex;
}

还有一句俏皮话:

let i = arr.indexOf(Math.max(...arr));

尽管如此,它执行的比较次数是必要的两倍,并且会在大型数组上抛出 RangeError。我会坚持函数。

如果我没记错的话,我会说这是为了编写自己的函数。

function findIndexOfGreatest(array) {
var greatest;
var indexOfGreatest;
for (var i = 0; i < array.length; i++) {
if (!greatest || array[i] > greatest) {
greatest = array[i];
indexOfGreatest = i;
}
}
return indexOfGreatest;
}

这个函数的稳定版本如下:

// not defined for empty array
function max_index(elements) {
var i = 1;
var mi = 0;
while (i < elements.length) {
if (!(elements[i] < elements[mi]))
mi = i;
i += 1;
}
return mi;
}

在一行中,可能比 arr.indexOf(Math.max.apply(Math, arr))更快:

var a = [0, 21, 22, 7];
var indexOfMaxValue = a.reduce((iMax, x, i, arr) => x > arr[iMax] ? i : iMax, 0);


document.write("indexOfMaxValue = " + indexOfMaxValue); // prints "indexOfMaxValue = 2"

地点:

  • iMax-到目前为止最好的索引(到目前为止最大元素的索引,在第一次迭代 iMax = 0上,因为 reduce()的第二个参数是 0,在我们的例子中我们不能省略 reduce()的第二个参数)
  • x-数组中当前测试的元素
  • i-当前测试的索引
  • 我们的数组([0, 21, 22, 7])

关于 reduce()方法(摘自 David Flanagan 的“ JavaScript: The Definition Guide”) :

Reduce ()有两个参数。第一个是执行约简操作的函数。这个约简函数的任务是以某种方式将两个值合并或约简为一个值,并返回该约简值。

与 reduce ()一起使用的函数不同于与 forEach ()和 map ()一起使用的函数。熟悉的值、索引和数组值作为第二个、第三个和第四个参数传递。第一个论点是迄今为止削减的累积结果。在第一次调用该函数时,第一个参数是作为 在后续调用中,它是前一次函数调用返回的值。

当您在没有初始值的情况下调用 reduce ()时,它使用数组的第一个元素作为初始值。这意味着对约简函数的第一个调用将使用第一个和第二个数组元素作为其 第一次和第二次辩论。

编辑: 几年前,我给出了一个答案,这是恶心的,太具体,太复杂。所以我在编辑。我更喜欢上面的函数式答案,因为它们的整洁性,而不是它们的可读性; 但是如果我更熟悉 javascript,那么我可能也会因此喜欢它们。

伪代码:

包含最大值的跟踪索引。假设索引0最初是最大的。与当前指数进行比较。必要时更新具有最大值的索引。

密码:

var mountains = [3, 1, 5, 9, 4];


function largestIndex(array){
var counter = 1;
var max = 0;


for(counter; counter < array.length; counter++){
if(array[max] < array[counter]){
max = counter;
}
}
return max;
}


console.log("index with largest value is: " +largestIndex(mountains));
// index with largest value is: 3

 var arr=[0,6,7,7,7];
var largest=[0];
//find the largest num;
for(var i=0;i<arr.length;i++){
var comp=(arr[i]-largest[0])>0;
if(comp){
largest =[];
largest.push(arr[i]);
}
}
alert(largest )//7
 

//find the index of 'arr'
var arrIndex=[];
for(var i=0;i<arr.length;i++){
var comp=arr[i]-largest[0]==0;
if(comp){
arrIndex.push(i);
}
}
alert(arrIndex);//[2,3,4]

如果你正在使用下划线,你可以使用这个漂亮的简短的一行程序:

_.indexOf(arr, _.max(arr))

它将首先找到数组中最大项的值,在本例中为22。然后它将返回数组中22所在位置的索引,在本例中为2。

使用 reduce的另一个 max 解决方案:

[1,2,5,0,4].reduce((a,b,i) => a[0] < b ? [b,i] : a, [Number.MIN_VALUE,-1])
//[5,2]

如果数组为空,则返回 [5e-324, -1]。如果只想要索引,则将 [1]放在。

最少经过(改为 >MAX_VALUE) :

[1,2,5,0,4].reduce((a,b,i) => a[0] > b ? [b,i] : a, [Number.MAX_VALUE,-1])
//[0, 3]
function findIndicesOf(haystack, needle)
{
var indices = [];


var j = 0;
for (var i = 0; i < haystack.length; ++i) {
if (haystack[i] == needle)
indices[j++] = i;
}
return indices;
}

array传递给 haystack,将 Math.max(...array)传递给 needle。这将为数组提供 所有 max 元素,并且它更具可扩展性(例如,您还需要查找 min 值)

如果创建数组的一个副本并对其进行降序排序,则副本的第一个元素将是最大的。可以在原始数组中找到它的索引。

var sorted = [...arr].sort((a,b) => b - a)
arr.indexOf(sorted[0])

复制的时间复杂度为 O (n) ,排序的时间复杂度为 O (n * log (n)) ,indexOf 的时间复杂度为 O (n)。

如果你需要更快的速度,Ry 的答案是 O (n)。

为了完成@VFDan 的工作,我对3个方法进行了基准测试: 接受的方法(自定义循环)、 reduce 和 find (max (arr)) ,其数组为10000个浮点数。

Chromum85 linux 上的结果(越高越好) :

  • 自定义循环: 100%
  • 减幅: 94.36%
  • 最大指数: 70%

Firefox 80 linux 上的结果(越高越好) :

  • 自定义循环: 100%
  • 减幅: 96.39%
  • 最高指数: 31.16%

结论:

如果需要代码快速运行,不要使用 indexOf (max)。 Reduce 是可以的,但是如果你需要最好的性能,可以使用自定义循环。

您可以使用以下链接在其他浏览器上运行此基准测试: Https://jsben.ch/wkd4c

对@traxium 解决方案的“ reduce”版本做了一个小小的修改,其中考虑到了空数组:

function indexOfMaxElement(array) {
return array.reduce((iMax, x, i, arr) =>
arr[iMax] === undefined ? i :
x > arr[iMax]           ? i : iMax
, -1            // return -1 if empty
);
}

要找到数组中最大值的索引,将原始数组复制到新数组中,然后按照递减顺序对原始数组进行排序以得到输出[22,21,7,0] ; 现在使用这个代码 copNumbers.indexOf (number [0])在 CopNumbers 数组中找到值22的索引;

<script>
const numbers = [0, 21, 22, 7];
const copyNumbers = [];
copyNumbers.push(...numbers);
numbers.sort(function(a, b){
return b - a
});
const index = copyNumbers.indexOf(numbers[0]);
console.log(index);
</script>

做这个

Const max = arr.reduce ((m,n) = > Math.max (m,n)) ,然后是 max 的索引

使用 findIndex 获取 index

Var index = arr.findIndex (i = > i = = = max)