资讯专栏INFORMATION COLUMN

复习Javascript专题(五):js中的循环遍历

mrli2016 / 2477人阅读

摘要:循环这个是最常用,也是最简单的循环了。常用于数组或者类数组的遍历。异步任务定时器,事件,回调函数等。循环它主要用来遍历对象,也可用来遍历数组。遍历对象时是属性名,而遍历数组是字符串格式的下标值。

for循环
这个是最常用,也是最简单的循环了。常用于数组或者类数组的遍历。
 for(let i=0;i<5;i++){
     console.log(`${i} is ${arr[i]}`);
 }

拓展:面试中经常爱考这样一道代码题:

    for(var i=0;i<5;i++){
        setTimeout(function(){
            console.log(i);
        },1000)
    }

问:最后分别打印出i的值是多少?

要注意,这里特意用了var声明,是因为let会有块级作用域,用let的话这段代码就很正常的打印出0,1,2,3了。

正常来说答案是5次5。
Ps:为什么说正常呢,我发现点CSDN的博客正文进去的控制台一直是打印5个1,我也不晓得为啥[/捂脸哭/]

这一道题就涉及了js的单线程和异步,闭包,作用域几个方面。

单线程的意思是同一时间不能分心,只能专心做一件事,而异步任务会先被插入到异步队列中,

只有当所有同步任务执行完毕后,栈被清空,才会读取任务队列里的任务并执行。

异步任务定时器,事件,回调函数等。
    
关于js线程这里有详细介绍:JS 演变、单线程、异步任务

说说作用域方面:其实上面的for循环等同于下面的写法:

var i=0;    
for(;i<5;i++){
    console.log(i)
}

由此可见,i是全局变量,所以在运行完后也没有销毁,而是一次次值被覆盖,直到最后一次。
因此,当执行定时器里面的函数时,同步任务已经执行完,但还是当拿到这个全局变量。

而这个问题有两个解决办法:作用域和闭包
作用域:把var改成let即可,因为let有块级作用域。
闭包:闭包的特性就是函数嵌套函数。

for(var i=0;i<5;i++){
    (function(i){
        setTimeout(function(){
            console.log(i);
        },1000)
    }(i))
}

每次for循环时都将i的值传入匿名函数,每次都创建了一个新的拥有私有变量i的匿名函数。

for in循环

它主要用来遍历对象,也可用来遍历数组。遍历对象时key是属性名,而遍历数组是字符串格式的下标值

缺点:它不能保证遍历顺序;不仅遍历自身属性,还会访问prototype上的属性。(可用hasOwnProperty加一层判断)
    let arr=["red","blue","green","grey"];
    for(let key in arr){
        console.log(`${key} is ${arr[key]}`);
    }
for of循环(ES6新增——遍历数组)

它可用来替代for in和forEach,它可以遍历 Arrays(数组/类数组), Strings(字符串), Maps(映射), Sets(集合)等可迭代(Iterable data)的数据结构,注意它的兼容性。
与for in区别:

a.它的key值代表的是value值。
b.它不能多带带遍历对象,因为获取不到对象的key值。
总的来说,对象用for in,数组用for of比较合适。

用法同for in就不重复了。

forEach循环(遍历数组)

它主要用来遍历数组,没有返回值
用法:arr.forEach(()=>(item,index,arr))

let arr=["red","blue","green","grey"];
arr.forEach(function(item,index,arr){
    console.log(`${index} is ${item}`);
    })

确实和ES6的map方法比较像。

map方法(ES6新增——遍历数组)

返回一个新数组,数组中的元素为原始数组元素调用函数处理后的值。我在React里用的话,经常是返回一个DOM结构。

let arr=["red","blue","green","grey"];
let result=arr.map((item,index,arr)=>{
        console.log(`${index} is ${item}`)
        return item;
    })
filter方法(数组内置方法)

看名字也知道是一个过滤功能,不过它不会改变原数组,只返回过滤后的元素,非常实用的一个方法,墙裂推荐。
参数和map一样。

   let arr=[3,53,43,65,32,5,52,64,2,64];
   let result=arr.filter((item)=>{return item%3=2;});
while 和 do while

讲真,while我用得很少,就是在算法里用过了。

while(条件为真){
    执行代码...
    循环条件变更
}
let n=1;
while(n<6){
    console.log("看进几次"); // 5次啦
    n++;
}

do while和while不同的是,它不管条件是否成立,反正都要走一次。
let n2=3;
do{
    console.log("至少走一次")            
    n++;
}while(n<3); // 这时候其实条件为假,但还是会进do的语句

平时工作就用到这些会比较多,日后有常用的再补充。

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/99356.html

相关文章

  • 复习Javascript专题(一):基本概念部分

    摘要:一数据类型基本类型引用类型类型判断返回结果未定义布尔值字符串数值对象或者函数拓展堆栈两种数据结构堆队列优先,先进先出由操作系统自动分配释放,存放函数的参数值,局部变量的值等。 一、数据类型 基本类型:`Null Boolean String Undefined Number(NB SUN)` 引用类型:`Array Function Object` 类型判断:typeof 返回结果...

    LiangJ 评论0 收藏0
  • 复习Javascript专题(四):js中的深浅拷贝

    摘要:基本数据类型的复制很简单,就是赋值操作,所以深浅拷贝也是针对,这类引用类型数据。它会抛弃对象的。另外,查资料过程中还看到这么一个词结构化克隆算法还有这一篇资料也有参考,也写得比较详细了的深浅拷贝 基本数据类型的复制很简单,就是赋值操作,所以深浅拷贝也是针对Object,Array这类引用类型数据。 浅拷贝对于字符串来说,是值的复制,而对于对象来说则是对对象地址的复制;而深拷贝的话,它不...

    MobService 评论0 收藏0
  • 复习Javascript专题(二):闭包,内存,以及垃圾回收机制

    摘要:一个闭包就是当一个函数返回时,一个没有释放资源的栈区所以参数和变量不会被垃圾回收机制回收。使用不当会很容易造成内存泄露。最后,垃圾回收器完成内存清除工作,销毁那些带标记的值并回收它们所占用的内存空间。 1.什么是闭包?闭包有啥特性以及存在什么问题? 概念:闭包是指有权访问另一个函数作用域中的变量的函数。下面的outer就形成了一个闭包: function outer(){ co...

    hankkin 评论0 收藏0
  • JavaScript专题之jQuery通用遍历方法each的实现

    摘要:语法为回调函数拥有两个参数第一个为对象的成员或数组的索引,第二个为对应变量或内容。但是对于的函数,如果需要退出循环可使回调函数返回,其它返回值将被忽略。 JavaScript 专题系列第十一篇,讲解 jQuery 通用遍历方法 each 的实现 each介绍 jQuery 的 each 方法,作为一个通用遍历方法,可用于遍历对象和数组。 语法为: jQuery.each(object,...

    blankyao 评论0 收藏0
  • JS专题之数组去重

    摘要:将元素作为对象的键,默认键对应的值为如果对象中没有这个键,则将这个元素放入结果数组中去。 前言 数组去重在日常开发中的使用频率还是较高的,也是网上随便一抓一大把的话题,所以,我写这篇文章目的在于归纳和总结,既然很多人都在提的数组去重,自己到底了解多少呢。又或者是如果自己在开发中遇到了去重的需求,自己能想到更好的解决方案吗。 这次我们来理一理怎么做数组去重才能做得最合适,既要考虑兼容性,...

    only_do 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<