在 JavaScript 中循环遍历数组的最快方法是啥?

Posted

技术标签:

【中文标题】在 JavaScript 中循环遍历数组的最快方法是啥?【英文标题】:What's the fastest way to loop through an array in JavaScript?在 JavaScript 中循环遍历数组的最快方法是什么? 【发布时间】:2011-07-17 23:47:55 【问题描述】:

我从书上了解到,你应该这样写for循环:

for(var i=0, len=arr.length; i < len; i++)
    // blah blah

因此不会每次都计算arr.length

其他人说编译器会对此做一些优化,所以你可以写:

for(var i=0; i < arr.length; i++)
    // blah blah

我只是想知道哪种方法在实践中是最好的?

【问题讨论】:

在处理数组循环时也值得一看:jsperf.com/array-loop-var-caching @wong2 Tthis benchmark from Browserdiet 有更完整的替代品集合。 jsben.ch/#/y3SpC 在之前的jsben上改进:jsben.ch/#/R6LbS 我们可以在本次比赛中引入for ... of 循环吗?语法似乎比没有缓存的 for 循环更容易,我想知道是否应该切换到使用 for of 循环。 【参考方案1】:

我总是以第一种风格写作。

即使编译器足够聪明,可以针对数组优化它,但如果我们在这里使用 DOMNodeList 或一些具有计算长度的复杂对象,它仍然很聪明?

我知道关于数组的问题是什么,但我认为以一种样式编写所有循环是一种好习惯。

【讨论】:

【参考方案2】:

循环遍历 javascript 数组的绝对最快方法是:

var len = arr.length;
while (len--) 
    // blah blah

完整比较请参见this post

【讨论】:

别忘了使用var(否则len会变成一个全局变量)。此外,请参阅 jsperf.com/loops 了解更多循环基准。 这个答案所基于的博文现在已经快 4 年了,当时 js 引擎发生了很多变化,请参阅下面的答案以获得更新的比较。 我同意@jondavidjohn。我测试了这段代码,结果证明效率较低...检查 jsperf.com/caching-array-length/84 上述答案几乎普遍(跨浏览器)比 for 循环慢得多。请参阅已接受答案中的 JSPerf 链接。太可惜了,因为它在 IMO 上的可读性极强。 我猜@jondavidjohn 你的意思是“我在下面的答案”是“我在上面的答案”哈哈。【参考方案3】:

如果顺序不重要,我更喜欢这种风格:

for(var i = array.length; i--; )

它会缓存长度并且写起来要短得多。但它会以相反的顺序遍历数组。

【讨论】:

你刚刚杀了它。 你不需要 i >= 0;? @MarwaAhmad: 否。i-- 返回一个数字,一旦该数字为0,条件为false,因为Boolean(0) === false【参考方案4】:

使用大多数现代浏览器执行此测试后: https://jsben.ch/wY5fo

目前,最快的循环形式(在我看来也是最明显的语法)。

具有长度缓存的标准 for 循环

    var i = 0, len = myArray.length;
    while (i < len) 
        // your code
        i++
    

我想说,这绝对是我为 JavaScript 引擎开发人员鼓掌的一个案例。运行时应该针对清晰而不是聪明进行优化。

【讨论】:

有趣的是,在 IE9 中这更快: for (var i = 0, len = myArray.length; i 查看Prefer prefix operators over postfix 其他原因使用++i 我按照@BennettMcElwee 的建议使用前缀运算符进行了测试,它运行得更快一点:for(var i=0, len=myArray.length; i&lt;len; ++i) Check jsperf.com/caching-array-length/84 你必须小心使用这个循环。我开始使用它并且由于我犯的一个错误而难以跟踪错误。如果像这样嵌套两个循环:jsfiddle.net/KQwmL/1。您必须小心在两个循环中以不同的方式命名 var len,否则第二个循环将覆盖第一个 len。 @WillshawMedia 您可以使用单个 var 语句声明多个变量。它是如何编写的,len 实际上是按照您的建议进行的。【参考方案5】:

http://jsperf.com/caching-array-length/60

我准备的最新版本的测试(通过重用旧版本)显示了一件事。

缓存长度没有那么重要,但也无妨。

上面链接的测试的每次第一次运行(在新打开的选项卡上)在我的 Debian Squeeze 64 中的 Chrome、Opera 和 Firefox 中的最后 4 个 sn-ps(图表中的第 3、5、7 和 10 位)都给出了最佳结果-位(my desktop hardware)。随后的运行给出了完全不同的结果。

性能方面的结论很简单:

使用 for 循环(转发)并使用 !== 而不是 &lt; 进行测试。 如果以后不必重用数组,那么 while 循环减少长度和破坏性 shift()-ing 数组也是有效的。

tl;博士

现在(2011.10)下面的模式看起来是最快的。

for (var i = 0, len = arr.length; i !== len; i++) 
    ...

请注意,缓存 arr.length 在这里并不重要,因此您只需测试 i !== arr.length,性能不会下降,但您会得到更短的代码。


PS:我知道在带有shift() 的 sn-p 中,它的结果可以用来代替访问第 0 个元素,但是在重用以前的修订版(有错误的 while 循环)之后,我不知何故忽略了这一点,后来我没有想要失去已经获得的结果。

【讨论】:

在循环中创建变量,如 let current = arr[i] 会降低性能(大内存分配)?还是在循环之前声明 current 会更好?还是在循环内的所有地方都使用 arr[i]? 在循环之前声明循环要使用的任何变量【参考方案6】:

我所知道的最优雅的解决方案是使用地图。

var arr = [1,2,3];
arr.map(function(input)console.log(input););

【讨论】:

问题不是要以最慢的方式遍历循环【参考方案7】:

“最佳”是纯粹的表现吗?还是性能AND可读性?

纯性能“最好”就是这个,它使用缓存和 ++prefix 运算符(我的数据:http://jsperf.com/caching-array-length/189)

for (var i = 0, len = myArray.length; i < len; ++i) 
  // blah blah

我认为无缓存的 for 循环是执行时间和程序员阅读时间的最佳平衡。每个从 C/C++/Java 开始的程序员都不会浪费一毫秒时间阅读这篇文章

for(var i=0; i < arr.length; i++)
  // blah blah

【讨论】:

+1 以提高可读性。不管len 的名字有多好,人们总是需要对第一个循环进行双重处理。第二个循环的意图很明显。【参考方案8】:

2014 While回来了

只要合乎逻辑。

看看这个

for( var index = 0 , length = array.length ; index < length ; index++ ) 

 //do stuff


    需要创建至少 2 个变量(索引、长度) 需要检查索引是否小于长度 需要增加索引 for 循环有 3 个参数

现在告诉我为什么这应该比:

var length = array.length;

while( --length )  //or length--

 //do stuff


    一个变量 没有检查 索引减少(机器更喜欢) while只有一个参数

当 Chrome 28 显示 for 循环比 while 循环快时,我完全糊涂了。 这一定是某种

“嗯,每个人都在使用 for 循环,让我们专注于 为 chrome 开发。”

但是现在,在 2014 年,while 循环又回到了 chrome 上。它快 2 倍,在其他/旧版浏览器上总是更快。

最近我做了一些新的测试。现在在现实世界中,这些短代码一文不值,jsperf 实际上无法正确执行 while 循环,因为它需要重新创建 array.length,这也需要时间。

您无法在 jsperf 上获得 while 循环的实际速度。

您需要创建自己的自定义函数并使用window.performance.now() 进行检查

是的...... while 循环不可能更快。

真正的问题实际上是 dom 操作/渲染时间/ 绘制时间或者你想怎么称呼它。

例如,我有一个画布场景,我需要计算坐标和碰撞...这是在 10-200 微秒(不是毫秒)之间完成的。渲染所有内容实际上需要不同的毫秒数。与 DOM 中相同。

但是

在某些情况下还有另一种超级高效的方式使用 for loop...例如复制/克隆数组

for(
 var i = array.length ;
 i > 0 ;
 arrayCopy[ --i ] = array[ i ] // doing stuff
);

注意参数的设置:

    与 while 循环相同,我只使用一个变量 需要检查索引是否大于0; 正如您所看到的,这种方法与每个人使用的普通 for 循环不同,因为我在第三个参数内进行处理,并且我也直接在数组内减少。

这么说,这证实了机器之类的 --

我想把它写得更短一点,去掉一些无用的东西,然后用同样的风格写这个:

for(
 var i = array.length ;
 i-- ;
 arrayCopy[ i ] = array[ i ] // doing stuff
);

即使它更短,看起来再使用一次i 也会减慢一切。 它比之前的 for 循环和 while 慢 1/5。

注意:在没有的for loo之后;非常重要

即使我只是告诉你 jsperf 不是测试脚本的最佳方式 .. 我在这里添加了这 2 个循环

http://jsperf.com/caching-array-length/40

这是关于 javascript 性能的另一个答案

https://***.com/a/21353032/2450730

这个答案是为了展示编写 javascript 的高效方式。因此,如果您看不懂,请询问,您会得到答案或阅读有关 javascript 的书http://www.ecma-international.org/ecma-262/5.1/

【讨论】:

这个答案从非常好开始。我注意到过去几年 forwhile 更快,我曾经在 crome-dev 上读到这正是因为你提到的原因。 while 再次赶上只是时间问题。从那时起,您答案第一部分的逻辑将成立(再一次,耶)! 然而现代实现不再严格遵循每个 ecma 指定的步骤(它们进行了优化)。由于现在您的引擎不再是最明显的瓶颈,您现在可以真正注意到 反向循环中的 CPU 缓存未命中 解释一下,也许我可以更正答案或学习新东西。顺便说一句,答案现在已经有一年多了......浏览器可能会像往常一样随着时间而改变...... 在我看来,while( --length ) 是邪恶的,因为虽然它在技术上有效,因为 0 是错误的,但从语义上讲,0 和 false 并不是真正的同一件事。 是的……这是一篇较旧的帖子……但是我喜欢简单的时间。当然,当你在这两种情况下提到它时,你需要知道要写什么。另一方面,我从来没有必要循环负数。 小心,当index0 时,index-- 将评估为false,如果您正在迭代数组中的所有内容,您不希望这样做【参考方案9】:
var arr = []; // The array
var i = 0;
while (i < arr.length) 
    // Do something with arr[i]
    i++;

i++ 比 ++i、--i 和 i-- 快

此外,您可以在最后一次需要访问 i 时保存执行 arr[i++] 的最后一行(但这可能很难调试)。

你可以在这里测试它(与其他循环测试):http://jsperf.com/for-vs-whilepop/5

【讨论】:

目前在 Chrome 53 中确实如此,但 Firefox 48 具有相同的速度 - 检查 perfjs.info/array-iteration thunderguy.com/semicolon/2002/08/13/… 说++i 更快...【参考方案10】:

我尝试了一些其他方法来迭代一个巨大的数组,并发现将数组长度减半,然后在一个循环中迭代两半会更快。在处理巨大的数组时可以看到这种性能差异。

var firstHalfLen =0;
var secondHalfLen = 0;
var count2=0;
var searchterm = "face";
var halfLen = arrayLength/2;
if(arrayLength%2==halfLen)

   firstHalfLen = Math.ceil(halfLen);
   secondHalfLen=Math.floor(halfLen);

else

   firstHalfLen=halfLen;
   secondHalfLen=halfLen;

for(var firstHalfCOunter=0,secondHalfCounter = arrayLength-secondHalfLen;
    firstHalfCOunter < firstHalfLen;
    firstHalfCOunter++)

  if(mainArray[firstHalfCOunter].search(new RegExp(searchterm, "i"))> -1)
  
    count2+=1;
  
  if(secondHalfCounter < arrayLength)
  
    if(mainArray[secondHalfCounter].search(new RegExp(searchterm, "i"))> -1)
    
        count2+=1;
    
    secondHalfCounter++; 
  

缓存长度for-loop VS上述方法的一些性能比较(使用timer.js)。

http://jsfiddle.net/tejzpr/bbLgzxgo/

【讨论】:

【参考方案11】:

**缓存循环内的数组长度,几秒钟的时间会被忽略。取决于数组中的项目,如果数组中有更多项目,则时间的 Ms 有很大差异*

**

sArr; //Array[158];

for(var i = 0 ; i <sArr.length ; i++) 
 callArray(sArr[i]); //function call


***end: 6.875ms***

**

**

sArr; //Array[158];
for(var i = 0,len = sArr.length ; i < len ; i++) 
  callArray(sArr[i]); //function call


***end: 1.354ms***

**

【讨论】:

【参考方案12】:

另一个 jsperf.com 测试:http://jsperf.com/while-reverse-vs-for-cached-length

反向while循环似乎是最快的。唯一的问题是 while (--i) 将停止在 0。那么我如何在循环中访问 array[0]?

【讨论】:

如果你做while (i--),那么i的真实性将在递减之前测试,而不是递减然后测试真实性。【参考方案13】:

到目前为止,这个looks to be the fastest way...

var el;
while (el = arr.shift()) 
  el *= 2;

考虑到这会消耗数组,吃掉它,什么都不剩...

【讨论】:

arr.shift(); 而不是arr.pop() 这样可以避免数组反转。 @Gargaroz 如果您从网络服务获取 JSON,例如聊天服务或产品目录上的项目。只需要使用一次数组的另一种情况是,例如,图表会以间隔为基础获取许多坐标。例子很多。 酷,谢谢你的解释,你真好;你能指出我可以找到更多示例来利用这种循环的方向吗? 目前在 Chrome 53 和 Firefox 48 中,这是最慢的方法之一 - 检查 perfjs.info/array-iteration @Alireza 同意,我的回答中对此也有评论。【参考方案14】:

截至 2016 年 6 月,在最新的 Chrome 中进行一些测试(2016 年 5 月占浏览器市场的 71%,并且还在增加):

最快的循环是 for 循环,无论有没有缓存长度,都可以提供非常相似的性能。 (具有缓存长度的 for 循环有时比没有缓存的循环提供更好的结果,但差异几乎可以忽略不计,这意味着引擎可能已经优化为支持标准并且可能是最简单的不带缓存的 for 循环)。 带减量的 while 循环比 for 循环慢大约 1.5 倍。 使用回调函数(如标准 forEach)的循环比 for 循环慢大约 10 倍。

我认为这个线程太老了,它误导程序员认为他们需要缓存长度,或者使用带减量的反向遍历来获得更好的性能,编写的代码比简单直接的代码更易读且更容易出错for 循环。因此,我建议:

如果您的应用程序迭代了很多项,或者您的循环代码位于经常使用的函数中,那么直接的 for 循环就是答案:

for (var i = 0; i < arr.length; i++) 
  // Do stuff with arr[i] or i

如果您的应用程序并没有真正迭代大量项目,或者您只需要在这里和那里进行小迭代,则使用标准 forEach 回调或您选择的 JS 库中的任何类似函数可能更容易理解并且不太容易错误,因为索引变量范围是封闭的,你不需要使用括号,直接访问数组值:

arr.forEach(function(value, index) 
  // Do stuff with value or index
);

如果您在迭代数十亿行时确实需要几毫秒的时间,并且数组的长度在整个过程中不会发生变化,您可以考虑在 for 循环中缓存长度。虽然我认为现在这真的没有必要:

for (var i = 0, len = arr.length; i < len; i++) 
  // Do stuff with arr[i]

【讨论】:

不。 jsbench.github.io/#67b13d4e78cdd0d7a7346410d5becf12 显示最快的是“反向循环、隐式比较、内联代码”(105,221 操作/秒),而“循环、缓存值、内联代码”的得分仅为 76,635 操作/秒(Chrome 38.0.2125.111) @Fr0sT 您的基准测试是一个不同的场景,遍历从索引 1 到 Kyopaxa 将基准更改为 (0 @Fr0sT 如果您更改从零开始的缓存 for 循环而不进行相等比较,例如 for(let i=0, j=array.length; i &lt; j; i++),则前向 for 循环会大大加快。在一些测试中我运行它赢了,在大多数情况下它都在误差范围内或反向循环内。 @IsaacB 和所有,对不起,我没有注意到长凳完全不正确 - 所有直接循环迭代 1..length 而反向循环迭代 length..0(arr[length] 项无效)。我修复了测试,现在它们显示以下结果:“循环,内联代码”360,616 ops/sec ±0.27%,“循环,缓存值,内联代码”345,786 ops/sec ±2.18%(原文如此!)“反向循环,隐式比较,内联代码” 322,640 ops/sec ±2.90% (!!!)。测试由FF51执行。新板凳在这里jsbench.github.io/#6bdfcd2692ba80c16a68c88554281570。所以看起来丑化循环是没有意义的。【参考方案15】:

现在是 2017 年

我做了一些测试。

https://jsperf.com/fastest-way-to-iterate-through-an-array/

看起来while 方法在 Chrome 上是最快的。

在 Firefox 上,左减量 (--i) 似乎比其他减量 (++ii--i++) 快得多。

这种方法是平均禁食。但它以相反的顺序迭代数组。

let i = array.length;
while (--i >= 0) 
    doSomething(array[i]);

如果远期顺序很重要,请使用此方法。

let ii = array.length;
let i = 0;
while (i < ii) 
    doSomething(array[i]);
    ++i;

【讨论】:

通过使用关键字 let,您实际上是在比较范围创建性能而不是循环性能。 在您的 for 循环中使用 let i = 0, ii = array.length 将为for 块内的那些变量。您的 while 示例不会为 while 块内的变量创建新范围,这就是它们更快的原因。如果您在 for 循环中使用 var 而不是 let,您将看到 for 循环在 2017 年仍然与 while 一样快,但更具可读性。 这是我正在谈论的 jsperf:jsperf.com/javascript-loop-testing-let-vs-var 这只是 Chrome 中的一个问题。在其他浏览器中varlet 具有相同的性能 - ***.com/a/32345435/1785975 有趣。无论如何,我认为“while 在 Chrome 中更快”的说法并不准确。仅当使用 let 时,由于 Chrome 中该关键字的性能问题。如果使用var 或与其他浏览器一起使用,forwhile 几乎相同,有时for 甚至更快,具体取决于基准测试,并且更紧凑和更易读恕我直言。【参考方案16】:

截至 2017 年 9 月,these jsperf tests 显示以下模式在 Chrome 60 上的性能最高:

function foo(x) 
 x;
;
arr.forEach(foo);

有人可以复制吗?

【讨论】:

是的,它似乎是最快的,但是尝试在 IE11 中运行它,这些选项是最慢的。在 Firefox 55.03 中,“旧缓存 len”达到 1200 万,与 3.3k 的 chrome 相比,这是一个惊人的性能。为了在所有浏览器中保持一致的性能,您应该为每个浏览器使用最快的平均循环。【参考方案17】:

基本的 while 循环通常是最快的。 jsperf.com 是测试这些类型概念的绝佳沙盒。

https://jsperf.com/fastest-array-loops-in-javascript/24

【讨论】:

【参考方案18】:

这只是 2018 年,所以更新可能会很好......

我真的不得不不同意接受的答案。 它在不同的浏览器上有所不同。有些更快forEach,有些for-loop,还有一些while 这是所有方法的基准http://jsben.ch/mW36e

arr.forEach( a => 
  // ...

因为你可以看到很多像 for(a = 0; ... ) 这样的 for 循环,所以值得一提的是,如果没有 'var' 变量将在全局范围内定义,这会极大地影响速度,因此它会变慢。

Duff 的设备在 Opera 上运行得更快,但在 Firefox 上却不行

var arr = arr = new Array(11111111).fill(255);
var benches =     
[ [ "empty", () => 
  for(var a = 0, l = arr.length; a < l; a++);
]
, ["for-loop", () => 
  for(var a = 0, l = arr.length; a < l; ++a)
    var b = arr[a] + 1;
]
, ["for-loop++", () => 
  for(var a = 0, l = arr.length; a < l; a++)
    var b = arr[a] + 1;
]
, ["for-loop - arr.length", () => 
  for(var a = 0; a < arr.length; ++a )
    var b = arr[a] + 1;
]
, ["reverse for-loop", () => 
  for(var a = arr.length - 1; a >= 0; --a )
    var b = arr[a] + 1;
]
,["while-loop", () => 
  var a = 0, l = arr.length;
  while( a < l ) 
    var b = arr[a] + 1;
    ++a;
  
]
, ["reverse-do-while-loop", () => 
  var a = arr.length - 1; // CAREFUL
  do 
    var b = arr[a] + 1;
   while(a--);   
]
, ["forEach", () => 
  arr.forEach( a => 
    var b = a + 1;
  );
]
, ["for const..in (only 3.3%)", () => 
  var ar = arr.slice(0,arr.length/33);
  for( const a in ar ) 
    var b = a + 1;
  
]
, ["for let..in (only 3.3%)", () => 
  var ar = arr.slice(0,arr.length/33);
  for( let a in ar ) 
    var b = a + 1;
  
]
, ["for var..in (only 3.3%)", () => 
  var ar = arr.slice(0,arr.length/33);
  for( var a in ar ) 
    var b = a + 1;
  
]
, ["Duff's device", () => 
  var len = arr.length;
  var i, n = len % 8 - 1;

  if (n > 0) 
    do 
      var b = arr[len-n] + 1;
     while (--n); // n must be greater than 0 here
  
  n = (len * 0.125) ^ 0;
  if (n > 0)  
    do 
      i = --n <<3;
      var b = arr[i] + 1;
      var c = arr[i+1] + 1;
      var d = arr[i+2] + 1;
      var e = arr[i+3] + 1;
      var f = arr[i+4] + 1;
      var g = arr[i+5] + 1;
      var h = arr[i+6] + 1;
      var k = arr[i+7] + 1;
    
    while (n); // n must be greater than 0 here also
  
]];
function bench(title, f) 
  var t0 = performance.now();
  var res = f();
  return performance.now() - t0; // console.log(`$title took $t1-t0 msec`);

var globalVarTime = bench( "for-loop without 'var'", () => 
  // Here if you forget to put 'var' so variables'll be global
  for(a = 0, l = arr.length; a < l; ++a)
     var b = arr[a] + 1;
);
var times = benches.map( function(a) 
                      arr = new Array(11111111).fill(255);
                      return [a[0], bench(...a)]
                     ).sort( (a,b) => a[1]-b[1] );
var max = times[times.length-1][1];
times = times.map( a => a[2] = (a[1]/max)*100; return a;  );
var template = (title, time, n) =>
  `<div>` +
    `<span>$title &nbsp;</span>` +
    `<span style="width:$3+n/2%">&nbsp;$Number(time.toFixed(3))msec</span>` +
  `</div>`;

var strRes = times.map( t => template(...t) ).join("\n") + 
            `<br><br>for-loop without 'var' $globalVarTime msec.`;
var $container = document.getElementById("container");
$container.innerhtml = strRes;
body  color:#fff; background:#333; font-family:helvetica; 
body > div > div   clear:both   
body > div > div > span 
  float:left;
  width:43%;
  margin:3px 0;
  text-align:right;

body > div > div > span:nth-child(2) 
  text-align:left;
  background:darkorange;
  animation:showup .37s .111s;
  -webkit-animation:showup .37s .111s;

@keyframes showup  from  width:0;  
@-webkit-keyframes showup  from  width:0;  
&lt;div id="container"&gt; &lt;/div&gt;

【讨论】:

@Maykonn 你可能想说“它在任何地方都可以使用,除了 Opera Mini” @Maykonn 默认视图中没有列出,因为 0.18% 的用户拥有 IE8,您不应该浪费时间尝试支持它; 2018 年是一匹死马。 如果您考虑到世界各地的所有用户,这绝对是正确的。但是,不幸的是,IE8 在世界的特定地区仍然适用。 如果可以的话,不仅不同的浏览器使用不同的方法会有不同的结果,同样的浏览器也会有不同的输入不同的结果。一个巨大的纯数字数组将得到非常优化,而一个小的混合数组则不会。 for..of 和 for..in 怎么样?【参考方案19】:

while 循环比 for 循环快一点。

var len = arr.length;
while (len--) 
    // blah blah

改用 for 循环

【讨论】:

【参考方案20】:

试试这个:

var myarray =[],
i = myarray.lenght;
while(i--)
// do somthing

【讨论】:

【参考方案21】:

截至 2019 年 WebWorker 已经越来越流行,对于大型数据集,我们可以通过充分利用多核处理器,使用 WebWorker 更快地处理。

我们还有Parallel.js,它使WebWorker 更易于用于数据处理。

【讨论】:

【参考方案22】:

最快的方法是传统的 for 循环。这是更全面的性能比较。

https://gists.cwidanage.com/2019/11/how-to-iterate-over-javascript-arrays.html

【讨论】:

【参考方案23】:

如果您想要更快的 for 循环,请在循环外定义变量并使用以下语法

  const iMax = lengthOftheLoop;
  var i = 0;
  for (; i < iMax; i++) 
    console.log("loop"+i);
  

参考:https://medium.com/kbdev/voyage-to-the-most-efficient-loop-in-nodejs-and-a-bit-js-5961d4524c2e

【讨论】:

【参考方案24】:

虽然是个很老的问题,但是很有意思,

请原谅我稍微调整了一下问题,但我会在最后回答。

这个问题让我问自己是否有更好的 js 循环方法:

所以我做了一些测试,结果如下:

1000_000 条记录:最好的是 forEach。

100 条记录:根本没关系。


回到你的问题:

我创建的示例与问题不完全相同..但我发现了一些有趣的事情:

首先:就像你说的那样,如果 arr.length 在比较语句 i 内,它每次都会评估

注意:下面的arrLength变量不超过1000_000条记录的数量..

例如:这行不通

但这会

这将需要 0.036 秒 .. 与数字恒定时所需的时间相比非常大...


总结一下,

最好用 FOREACH

在你的情况下: i

查看测试: see the tests

【讨论】:

以上是关于在 JavaScript 中循环遍历数组的最快方法是啥?的主要内容,如果未能解决你的问题,请参考以下文章

循环遍历二维数组的最快方法?

使用 javascript 和循环获取所有正文元素

JS -javascript 数组遍历的几种方式,数组或对象循环遍历的对比分析,性能使用合理使用

在VBA(excel)中循环遍历行的最有效/最快的方法是啥?

一次循环遍历 Javascript 数组多个元素的惯用方法是啥?

请你告诉我合并两个数组,你有多少种方法