検索

ホームページ  >  に質問  >  本文

node.js中需要遍历数组并返回值的处理实在是搞不懂了...

var a = [[1,2,3],[4,5,6],[7,8,9]]
var b = []

const co = require('co');

new Promise(function(resolve, reject) {
  a.forEach(function(item) {
    item.forEach(function(it) {
      setTimeout(function () {
        b.push(it)
      }, 1000);
    })
  })
 // resolve(b)
}).then(function(data){
  console.log(data);
})

// 主要是异步的问题还是怎么的,会直接返回b = [] 而不是期待的
// b = [1,2,3,4,5,6,7,8,9]
高洛峰高洛峰2782日前619

全員に返信(3)返信します

  • 天蓬老师

    天蓬老师2017-04-17 14:43:26

    タイマーが実行される前に Promise がリゾルブ状態に変化し、then コールバックが実行されて b が出力されます。
    その後、タイマーがタイムアウトし、データが b に配置されます。
    解決は、タイマーを設定した直後に解決するのではなく、すべてのタイマーが期限切れになった後に実行する必要があります。

    new Promise(function(resolve, accept) {
      // コード
      //解決(b)
    }).then(関数(データ){
      コンソール.ログ(データ);
    })

    この Promise には解決または拒否がないため、常に保留状態となり、console.log に記録されません。したがって、解決行のコメントを解除するのを忘れたと思います。

     a.forEach(function(item) {
        item.forEach(関数(it) {
          setTimeout(関数() {
            b.プッシュ(それ)
          }, 1000);
        })
      })
      解決(b)

    Promise 内には、2 次元配列を横断するコードが含まれています。この 2 次元配列の各要素に対して、1 秒後に要素を b に追加するタイマーを設定します。タイマーを設定した後、Promise が最初に解決されます。まだ 1 秒に達しておらず、タイマーはまだ実行されておらず、b はまだ空の配列です。そして、解決したため、then が実行された後のステートメントが、発生した問題です。
    しばらく(1秒後)待ってからaを出力すると、実際に望む結果が得られます。 1 秒後、設定されたタイマーがタイムアウトしてトリガーされ、要素が b にプッシュされます。

    欲しい結果は次のように書く必要がありますか?

    var a = [[1,2,3],[4,5,6],[7,8,9]]
    var b = []
    
    new Promise(function(解決、拒否) {
      a.forEach(関数(項目) {
        item.forEach(関数(it) {
          setTimeout(function (item, it) {
            b.プッシュ(それ)
              if(item == a[a.length-1] && it == item[item.length -1]) {
              解決(b);
            }
          }、1000、アイテム、それ);
        })
      })
    }).then(関数(データ){
      コンソール.ログ(データ);
    })

    各タイマーで、私が 2 次元配列の最後のタイマーであれば解決します。それでおしまい。

    返事
    0
  • 迷茫

    迷茫2017-04-17 14:43:26

    var a = [[1,2,3],[4,5,6],[7,8,9]]
    var b = []
    
    new Promise(function(解決、拒否) {
    
      for (var i = 0; i 

    返事
    0
  • 阿神

    阿神2017-04-17 14:43:26

    非常にわかりにくい書き方になっているように感じますが、なぜ co があるのにそれを使用しないのですか?

    要素を 1 秒ごとにプッシュしたい場合は、これを実行できます。

    const a = [[1,2,3],[4,5,6],[7,8,9]]
    const b = []
    
    const Promise = (n) => new Promise((解決、拒否) => {
      const timer = setTimeout(() => {
        console.log('プッシュ', n)
        b.push(n)
        window.clearTimeout(タイマー)
        解決する()
      }、1000)
    })
    
    const c = a.reduce((prev, cur) => prev.concat(cur))
    
    const main = () => {
      console.log('開始')
      return c.reduce((prev, cur) => {
        return prev.then(() =>promise(cur))
      }、Promise.resolve())
    }
    
    main().then(() => console.log(b))

    返事
    0
  • キャンセル返事