迭代器是什么

112 阅读3分钟

什么是迭代,从表面去理解,日常我们最常见的最多的就是,需求迭代,产品迭代来了,可以理解,迭代的操作,一步一步来实现,做完一个需求,我们才能知道下一个需求需要做什么。从数据层面讲,一个数据按照一定顺序,不断取出数据的过程。这边很多人容易跟循环遍历混淆,下面我们顺带讲下区别

迭代:

强调是依次去数据,并不保证取多少,也不保证把所有数据取完,因为你永远不知道下一个是什么。

循环遍历:

循环遍历,首先你知道这个数据有多少。强调是把所有数据依次全部取出

迭代器

对迭代过程的封装,在不同的语言有不同的表现形式,通常为对象

  • 迭代器应该具备得到下一个数据的能力
  • 迭代器应该具有判断是否还有后续数据的能力

下面我们通过代码来解释迭代器 js规定,如果一个对象具有next方法,并且该方法返回一个对象,该对象格式如下:

//{value:xxx 值, done: xxx 是否迭代完成}
let obj = {
    next(){
        return {
               value:xxx,
               done: xx
        }
    }

}

则认为是一个迭代器 含义

  • next 是用来得到下一个数据
  • 返回的对象: value:下一个数据的值 done: boolean, 是否迭代完成

下面拿数组,来给他写一个迭代器

const arr = [1,2,3,4]
const iterator = {
                   i:0, // 当前数组下标
                   next(){
                       const result = {
                        value: arr[this.i],
                        done: arr[this.i + 1]? false : true
                      }
                       this.i++
                       return  result
                   }
                  }
  
console.log(iterator.next()) // ??
console.log(iterator.next()) // ??
console.log(iterator.next()) // ??
console.log(iterator.next()) // ??

最后打印结果是多少呢

console.log(iterator.next()) // { value: 1, done: false }
console.log(iterator.next()) // { value: 2, done: false }
console.log(iterator.next()) // { value: 3, done: false }
console.log(iterator.next()) // { value: 4, done: true }

我们把这个数组想象成一个库,从这个库里面拿取数据,这是我们使用这个迭代器,是不是不管这个数组数据怎么变,我们都可以通过迭代器进行迭代获取数据

function creatorIterator(arr){
    let i = 0;
     return {
            next(){
              const result = {
               value: arr[i],
               done: arr[i + 1]? false : true
             }
              this.i++
              return  result
          }
      }

};
const a = [1,2,3,4,5];
const b = ['a','b','c','d'];

// 我们基于a ,b 赋予迭代
const itera1 = creatorIterator(a);
const itera2 = creatorIterator(b);
// 可以在本地自己运行这个代码 实际操作看看这两个对象是什么

迭代器实现非波拉契

class Count {
  constructor(limit){

    this.limit = limit
  }
  
  [Symbol.iterator](){
    let pre1 = 1,pre2 = 1,
        limit = this.limit,
        n = 1;
    return {
      next(){
      
        if(pre1 + pre2 <= limit){
          let obj
          if(n <= 2){
            obj = {
              done:false,
              value:pre1
            }
          }else{
            obj = {
              done:false,
              value:pre1 + pre2
            }
            pre1 = pre2
            pre2 = obj.value
            
          }
          n++
        
          return obj
        }else{
          return {
            done:true,
            value:undefined
          }
        }
      }
    }
  }
}

let count = new Count(35)
console.log(count)
for(let i of count){
  console.log(i)
}
// 1
// 1
// 2
// 3
// 5
// 8
// 13
// 21
// 34

总结

我们通过随机给到一个数值,获取到这个数值之前的所有非波拉契数值,这边我们要注意的重点是,首先你不知道这个数值前面有哪些,其次,我们需要一次一次依次的获取他前面的值。所以我们需要深入的明白,强调是依次去数据,并不保证取多少,也不保证把所有数据取完,因为你永远不知道下一个是什么。

什么是生成器