代码改变世界

js中的循环总结一下子for in for of foreach Map等

2019-07-22 22:29  WEB前端小菜鸟  阅读(109)  评论(0)    收藏  举报

说裙子说,我最主要想说for of 

https://www.cnblogs.com/baiyunke/p/7821299.html

 

for of 不可以循环对象,可以把 对象arrary.from转成数组在用for of

 

 

 foreach会改变原数组,通常我用来处理后端返回的json 他返回的1代表已消费 2代表已过期这种格式

let arr=[1,3,5,7,9,11,5,1]
//当前值,下标,数组本身
arr.forEach((item,index,arr)=>{
console.log(item,index,arr);
})
通用只用得到item其他2个不写,forEach操作的原数组不会返回一个新数组
 
map() 方法返回一个新数组,数组中的元素为原始数组元素调用函数处理后的值。
let arr=[1,3,5,7,9,11,5,1]
    // 数组每个元素*2
    let bb=arr.map((item,index,arr)=>{
      return item * 2;
    })
    console.log(arr);
    console.log(bb);

map跟foreach一样接受三个参数,map要return  出来

 

for...in语句以任意顺序遍历一个对象自有的、继承的、可枚举的、非Symbol的属性。对于每个不同的属性,语句都会被执行。

for-in 循环主要用于遍历对象,数组也可以用

记住,for in遍历的是数组的索引(即键名),而for of遍历的是数组元素值。

 

for..of适用遍历数/数组对象/字符串/map/set等拥有迭代器对象的集合.但是不能遍历对象,因为没有迭代器对象.与forEach()不同的是,它可以正确响应break、continue和return语句

for-of循环不支持普通对象,但如果你想迭代一个对象的属性,你可以用for-in循环(这也是它的本职工作)或内建的Object.keys()方法:



面试的时候问了我for of能遍历对象吗?for in可以遍历原型链上的属性?
 for of 不能遍历对象,for in可以遍历原型链上的属性
 
eg: for in遍历
  mounted() {
    let obj = {
      name: "yu",
      age: 27
    };
    let arr = [9, 3, 4];
    let arr0 = [
      {
        name: "中文1",
        age: 31
      },
      {
        name: "中文3",
        age: 312
      }
    ];
    for (let item in obj) {
      console.log(item);
    }
    for (let item in arr) {
      console.log(item);
    }
    for (let item in arr0) {
      console.log(item);
    }
  }

  

for in 可以遍历对象也可以数组,如果是数组的话,不管你是普通类型数组还是引用类型的数组,它都只会遍历你的下标,如果是对象的话呢,它就会遍历类似于下标就是键,键值不会遍历如上图所示,

for in 可以遍历原型链上的属性,举个栗子

    let obj = {
      name: "yu",
      age: 27
    };
    obj.__proto__.lbj='勒布朗詹姆斯' //2种方式随便你
    Object.prototype.kob="科比";   // 修改Object.prototype  
    console.dir(obj);

  

 

 然后for in
  for (let key in obj) {
      console.log(key,obj[key]);//这里用obj.key得不到对象key的值,用obj[key] 或者 eval("obj."+key);
    }

  

 
循环结果如图
for in是可以遍历原型链上的属性的,如果只遍历对象自身的属性,而不遍历继承于原型链上的属性,使用hasOwnProperty 方法过滤一下
 for (let key in obj) {
      if(obj.hasOwnProperty(key)){
        console.log(key,obj[key]);//这里用obj.key得不到对象key的值,用obj[key] 或者 eval("obj."+key);
      }
    }

  

搞定for in 

 

接下来 for  of 

首先面试官for of 能遍历对象吗?答案不行

    let obj = {
      name: "yu",
      age: 27
    };
    let arr = [1, 25, 56];
    let arr1 = [
      {
        name: "lbj"
      },
      {
        name: "kobi"
      }
    ];
    for (let item of arr) {
      console.log(item);
    }
    for (let item of arr1) {
      console.log(item);
    }

  不管是普通类型数组还是引用类型数组,都是遍历的键值而不是下标,for in才是遍历的下标,当然你下标都拿到了还拿不到键值莫arr[下标]不久拿到了

 

现在来改一下用for of 遍历上面代码的obj

翻译一下对象是不可迭代的

这里学几个英文单词

iterable 可迭代的

iterator 迭代器

MDN解释(这就是为啥不可以迭代对象的原理)

 for...of语句在可迭代对象(包括 Array,Map,Set,String,TypedArray,arguments 对象等等)上创建一个迭代循环,调用自定义迭代钩子,并为每个不同属性的值执行语句

那怎么样才可以迭代对象呢

如下

类数组对象

 如果对象是一个类数组对象,那好办,用Array.from转成数组即可

  let obj = {
      0: "yu",
      1: 27,
      length:2
    };
    obj=Array.from(obj)
    for (let item of obj) {
      console.log(item);
    }

  

非类数组对象

如果不是类数组对象,也有办法,添加一个[Symbol.iterator]属性,并指向一个迭代器即可。

普通对象

let obj = {
name: "yu",
age: 27
};
console.dir(obj);

 

加上迭代器

let obj = {
      name: "yu",
      age: 27
    };
    obj[Symbol.iterator] = function(){
    var keys = Object.keys(this);
    var count = 0;
    return {
        next(){
            if(count<keys.length){
                return {value: obj[keys[count++]],done:false};
            }else{
                return {value:undefined,done:true};
            }
          }
        }
    };
    console.dir(obj);  

 

打印出来添加了迭代器之后的obj

 

 

在for of 就可以了

 

总结一下:for in既可以遍历数组也可以遍历对象,遍历数组时(不管是普通类型数组还是引用类型的),都便利的是下标,对象的话遍历的是键名,arr[下标]一样可以拿到键值

for of 不能遍历对象,除非做处理,遍历数组时,遍历的是键值