为了账号安全,请及时绑定邮箱和手机立即绑定

for循环中的i

bar中的i赋值为3 

在运行时是给for循环中的i赋值了?

正在回答

3 回答

我给你解释一下吧,希望能解释清楚。。

function foo(){
  function bar(){
     i = 3;
     console.log(i);
  }
  
  for(var i = 0;i<10;i++){
     bar(i * 2);
  }
}

foo();

由于局部变量声明提前,上面的代码相当于:

function foo(){
  
  var i; // js 引擎把变量声明提前了,但是并没有初始化

  function bar(){
     i = 3; // 这个i变量是foo的局部变量,而不是bar的局部变量
     console.log(i);
  }
  
  // 执行for循环时,i才初始化,此时i=0
  // 然后满足条件(0<10),进入循环
  // 在循环内部,调用bar函数,并把 i*2 作为实参传入(其实传不传参数都一样,可能是为了迷惑你)
  // 调用bar函数时,在内部引用了 i 变量,且这个 i 变量并不是bar函数的局部变量(因为没有用var)
  // bar内部的 i 变量其实时 bar 的上层执行环境即foo内的变量(如果你理解作用域和作用域链的话)
  // bar函数执行完,会把foo的i变量变为3
  
  // -------------死循环开始了
  
  // i++ 执行完,此时 i = 4
  // 4<10,满足条件,再一次进入循环,
  // 再次调用bar函数,又把i变成了3
  
  // i++ 执行完,此时 i = 4
  // 4<10,满足条件,再一次进入循环,
  // 再次调用bar函数,又把i变成了3
  
  // i++ 执行完,此时 i = 4
  // 4<10,满足条件,再一次进入循环,
  // 再次调用bar函数,又把i变成了3
  
  // .
  // .
  // . 
  for(i = 0;i<10;i++){
     bar(i * 2);
  }
}

foo();

希望我上面的分析你看明白了。。下面再说一下这个问题的变体。。

function foo(){
  function bar(){
     var i = 3; // 注意,与上面唯一不同是i前面有var
     console.log(i);
  }
  
  // 由于bar中的i变量使用了var声明,那么,bar中的i就是局部变量,与foo中的i不是同一个变量
  // 虽然两者名字相同,但绝不是同一个变量!!!记住!!!
  // 所以调用bar之后,改变的是bar内部的i,并不会影响foo中的i。。
  // 所以for循环能正确执行,你会看到for循环如你所愿执行了10次。。
  for(var i = 0;i<10;i++){
     bar(i * 2);
  }
}

foo();

额。。。作用域与作用域链是javascript中的难点和重点,需要一段时间来理解,如果你理解了他们的话,我上面的分析你差不多能看懂。如果不理解,请多关注这方面的知识点,攻坚一下。。然后在回来看这个问题你会豁然开朗。。。

5 回复 有任何疑惑可以回复我~
#1

x兔子 提问者

因为没有var 恍然大悟 =w=
2015-12-13 回复 有任何疑惑可以回复我~

死循环啊

0 回复 有任何疑惑可以回复我~

举报

0/150
提交
取消
慕课网技术沙龙之前端专场
  • 参与学习       35559    人
  • 解答问题       11    个

从实战到理论全方位解读前端技术,都是项目中的宝贵的经验

进入课程

for循环中的i

我要回答 关注问题
意见反馈 帮助中心 APP下载
官方微信