在多个for循环中使用相同的variables名是不好的做法吗?

我只是用JSHint编写了一些JavaScript代码。 在代码中我有两个for循环都使用这样的:

for (var i = 0; i < somevalue; i++) { ... } 

所以for循环都使用var i来进行迭代。

现在,JSHint向我展示了第二个for循环的错误:“'i'已经被定义了。 我不能说这是不正确的(因为它显然是),但我一直认为这并不重要,因为我只用在那个特定的地方。

以这种方式使用for-loop是不好的做法吗? 我应该为每个for循环在我的代码中使用不同的variables

 //for-loop 1 for (var i = 0; ...; i++) { ... } //for-loop 2 for (var j = 0; ...; j++) { ... } 

或者,这是我可以忽略的错误(因为它不会破坏我的代码,它仍然做它应该做的)?

JSLint btw。 因为我没有在函数顶部定义var i(这就是为什么我首先切换到JSHint),所以停止在第一个for循环validation。 所以根据这个问题的例子: 我应该使用JSLint或JSHint JavaScriptvalidation? – 无论如何,我应该使用for-loop来确认JSLint:

 ... var i; ... //for-loop 1 for (i = 0; ...; i++) { ... } ... //for-loop 2 for (i = 0; ...; i++) { ... } 

这对我来说也很好,因为这样我就可以避免JSLint和JSHint中的这两个错误。 但是我不确定的是,如果我应该为每个for循环使用一个不同的variables,像这样:

 ... var i, j; ... //for-loop 1 for (i = 0; ...; i++) { ... } //for-loop 2 for (j = 0; ...; j++) { ... } 

那么有没有一个最佳做法,或者我可以只用上面的任何代码,这意味着我select“我的”最佳做法?

由于variables声明被提升到它们出现的范围的顶部,所以解释器将以相同的方式有效地解释这两个版本。 出于这个原因,JSHint和JSLintbuild议将声明移出循环初始化程序。

下面的代码…

 for (var i = 0; i < 10; i++) {} for (var i = 5; i < 15; i++) {} 

…被有效地解释为:

 var i; for (i = 0; i < 10; i++) {} for (i = 5; i < 15; i++) {} 

请注意,我确实只有一个声明,并且有多个赋值 – 你不能在同一个范围内“重新声明”一个variables。

要真正回答你的问题…

有没有最佳做法,或者我可以只用上面的任何代码?

关于如何最好地处理这个问题有不同的意见。 就我个人而言,我同意JSLint,并认为当您在每个范围的顶部一起声明所有variables时,代码更清晰。 因为这就是代码的解释方式,所以为什么不编写看起来像它的代码呢?

但是,正如你所看到的那样,不pipe采取什么样的方法,代码都可以工作,所以这是一种风格/惯例的select,你可以使用任何你感觉最舒服的forms。

javascript中的variables是函数作用域(不是作用域的作用域)。

当你在一个循环中定义var i时,它仍然保留在循环中,也保留在循环中的函数中。

见下文,

 function myfun() { //for-loop 1 for (var i = 0; ...; i++) { ... } // i is already defined, its scope is visible outside of the loop1. // so you should do something like this in second loop. for (i = 0; ...; j++) { ... } // But doing such will be inappropriate, as you will need to remember // if `i` has been defined already or not. If not, the `i` would be global variable. } 

JSHint显示错误的原因是因为在JS中,variables作用域是函数,variables声明被悬挂在函数的顶部。

在Firefox中,您可以使用let关键字来定义块范围,但目前不支持其他浏览器。

let关键字包含ECMAScript 6规范。

我知道这个问题已经被回答,但是如果你想要超级for循环,写下来就像这样:

 var names = ['alex','john','paul','nemo'], name = '', idx = 0, len = names.length; for(;idx<len;++idx) { name = names[idx]; // do processing... } 

这里有几件事情…

  1. 数组长度正在存储在len 。 这会停止每个迭代JS评估names.length

  2. idx增量是一个预增值(例如++ idx NOT idx ++)。 预增量本来比后增量快。

  3. 存储对name的引用。 这是可选的,但build议如果您将使用namevariables很多。 每次调用names[idx]需要在数组中find索引。 无论这个search是一个线性search,树search还是散列表,search都还在发生。 因此,将参考存储在另一个variables中以减less查找。

最后,这只是我个人的偏好,我没有证据或任何性能好处。 不过,我总是喜欢将variables初始化为它们将要变为的types,例如name = '', ,。

仅在@TSCrowder的评论中提到过 :如果你的环境支持它(Firefox,Node.js),在ES6中你可以使用let声明

 //for-loop 1 for (let i = 0; ...; i++) { ... } //for-loop 2 for (let i = 0; ...; i++) { ... } 

将范围限制在for循环中 。 奖励:JSHint停止抱怨。

最好的做法是减lessvariables的范围,所以为循环声明迭代variables的最好方法是

 //for-loop 1 for (var i = 0; ...; i++) { ... } //for-loop 2 for (var j = 0; ...; j++) { ... } 

我知道用var声明variables的范围,但我在这里考虑代码的可读性。