JavaScript异步问题

JavaScript Asynchronous Issue

本文关键字:问题 异步 JavaScript      更新时间:2023-09-26

我正在尝试使用twitter API获取搜索结果,然后在将其显示在页面上之前对其进行修改。

我是异步函数的新手,我不知道如何对几个搜索字符串运行这种方法并处理结果:

var results = [];
for (string in searches) {
client.get('search/tweets', {q: searches[string]}, function(error, tweets, response){
   console.log(tweets); // I need to put these in an array (results) and get the next lot
});
}
analyse(results);

我需要多次运行搜索/推文,并建立一个结果数组,以便对其进行分析。如果我必须在函数中工作,我不知道该怎么做?将其放入回调函数也会遇到同样的问题。

对于这样的事情,我喜欢使用Promises。https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise

let promises = [];
// for each string you have create a new promise and put it in an array
for (string in searches) {
    promises.push(new Promise((resolve, reject) => {
        client.get('search/tweets', {q: searches[string]}, function(error, tweets, response){
           resolve(tweets);
        });
    }));
}
// after your loop use Promise.all to wait until all promises are resolved and then do something with the results
Promise.all(promises).then(results => {
    console.log(results); 
});

基本思想是:跟踪查询的搜索词数量,并在最后一个搜索词完成时处理分析。

var results = [];
var count = 0;
for (s in searches) {
    client.get('search/tweets', {q: searches[string]}, function(error, tweets, response){
       console.log(tweets); 
       results += tweets;
       if (++count == searches.count) analyse(results);
    });
}

还有更"现代"的异步代码处理方法,包括promise,我鼓励您在异步工作中查看这些方法。

这里基本上有两个工作部分。(1) 按间隔运行函数,并且(2) 进行异步调用。

每隔一段时间运行一个函数

第一种是以一定间隔运行函数的能力。这可以通过以下方式实现。

var myInterval = setInterval(function() {
  // do something here every second
}, 1000);

进行异步调用

第二种是进行异步调用。异步调用是异步的,因为在执行时不能保证结果存在您必须在异步调用的内部执行任何分析/数据操作这是保证响应的唯一方法。

根据您的示例,假设client.get()是异步调用,您将执行以下操作:

client.get('search/tweets', ..., function(err, tweets, response) {
  // perform some actions on the result
  analyse(tweets);
});

综合起来:

// make a request every second
var myInterval = setInterval(function() {
  // perform async operation
  client.get('search/tweets', ..., function(err, tweets, response) {   
    // perform operations on result
    analyse(tweets);
  });
}, 1000);
function analyse(tweets) {
  // do something with data here
});

听起来您希望这些请求串行工作(一次执行一个请求)。。。在纯JS中,它将类似于:

var results=[], i=0, l=searches.length;
var next=function(callback){
    if(i<l)
    {
        client.get("search/tweets", {q:searches[i]}, function(err, tweets, response){
            results.push(tweets);
            next(callback);
        });
    }
    else
    {
        callback(results);   
    }
};
next(function(results){
    analyze(results);
});

然而,正如realseanp所指出的,这些天来,Promises让这种方式变得更干净(尽管他的回答会并行运行请求)。