Dart - 帮助我理解Dart上的这段代码是如何工作的

时间:2014-10-24 08:18:12

标签: dart dart-async

请帮助我了解此代码的工作原理。为什么它以这种方式工作。

示例中的变量resStream<Row>

我想从Future<List>方法返回processQueryResult。这段代码可以正常工作,我得到的结果是正确的。

示例1

Future<List> processQueryResult(mysql.Results res) {
  List data = [];

  res.toList().then((List<mysql.Row> rows) {
    rows.forEach((mysql.Row row) {
      data.add({name: row.name, email: row.email});
    });
  });

  return new Future<List>(() {
    return data;
  });
}

结果data包含所有需要数据。

但请告诉我,为什么当我移动这段代码时

res.toList().then((List<mysql.Row> rows) {
  rows.forEach((mysql.Row row) {
    data.add({name: row.name, email: row.email});
  });
});

return new Future<List>(() {

  res.toList().then((List<mysql.Row> rows) {
    rows.forEach((mysql.Row row) {
      data.add({name: row.name, email: row.email});
    });
  });

  return data;

});

最后代码看起来(示例2 ):

Future<List> processQueryResult(mysql.Results res) {
  List data = [];      

  return new Future<List>(() {
    res.toList().then((List<mysql.Row> rows) {
      rows.forEach((mysql.Row row) {
       data.add({name: row.name, email: row.email});
      });
    });

    return data;
  });
}

然后在结果中我得到空列表。

对于测试我使用此功能:

testResult() {

  mysql.Results res = ... // get results;
  processQueryResult(res).then((data) {
    print(data);
  })

}

当代码processQueryResult喜欢示例1 时,我会得到正确的数据,但当代码processQueryResult喜欢示例2 时 - 我得到空列表。

请告诉我,为什么会这样?

如果您提供相应文章或文档的链接,我会很高兴。

1 个答案:

答案 0 :(得分:2)

return new Future<List>(() {

  res.toList() // <== 1.) registers a future for later execution // <== 3.) execute `toList()`
    .then((List<mysql.Row> rows) {
    rows.forEach((mysql.Row row) { // <== 4.) execute rows.forEach
      data.add({name: row.name, email: row.email});
    });
  });

  return data; // <== 2.) return data

});

3。)在调用上述代码的代码完成所有同步执行后执行

return new Future<List>(() {

  return res.toList() // <== returning the future keeps the async parts connected
                      // and one is executed after the other
    .then((List<mysql.Row> rows) {
      rows.forEach((mysql.Row row) { // <== 4.) execute rows.forEach
        data.add({name: row.name, email: row.email});
      });
    })
    .then((_) data);  // <== the same here, return data **after** the previous statements are finished
  });
});