Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/375.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 计算Node.js+;Redis+;Express.js和可爱的异步回调_Javascript_Node.js_Asynchronous_Express_Redis - Fatal编程技术网

Javascript 计算Node.js+;Redis+;Express.js和可爱的异步回调

Javascript 计算Node.js+;Redis+;Express.js和可爱的异步回调,javascript,node.js,asynchronous,express,redis,Javascript,Node.js,Asynchronous,Express,Redis,首先,请原谅我,这对我来说是一个非常未经授权的领域 获得以下信息: app.get('/user/:user_id/followings', function(req, res) { var response = {} , userId = req.params.user_id , ids = req.param('id').split(',') , prefix = 'user' , suffix = 'follower_ids';

首先,请原谅我,这对我来说是一个非常未经授权的领域

获得以下信息:

app.get('/user/:user_id/followings', function(req, res) {
    var response = {}
      , userId = req.params.user_id
      , ids = req.param('id').split(',')
      , prefix = 'user'
      , suffix = 'follower_ids';

    for (var i=0; i<ids.length; i++) {
      var id = ids[i]
        , key = prefix+':'+ids[i];

      console.log('1: ' + key);
      checkMembership(userId, id, key, suffix, function(error, reply){
        response[key] = reply;
        console.log('2: ' + key + ': ' + reply);
      });
    }

    res.json(response);
  });

  function checkMembership(userId, id, key, suffix, callback) {
    var lookup = key+':'+suffix;

    client.sismember(lookup, userId, callback);
  }
在浏览器中: {}

我知道这是因为事情是异步发生的。。。我只是不知道如何修复它

checkMembership功能中记录的密钥错误。控制台应输出第二次回调,如下所示:

2: user:1: 0
2: user:2: 1
2: user:3: 1
2: user:4: 1
2: user:1000: 0

救命啊

您是对的,这是因为checkMembership是异步的。因此,当checkMembership仍在等待答案时,for循环已完成

让我们从简化示例开始:

for (i = 0; i < 3; i += 1) {     

  console.log('inside: ', i);  

  process.nextTick(function () {  
    console.log('outside: ', i);    
  });                           

};      

console.log('end');   
因此,第一个问题是当计数器已经在2时执行回调。您可以通过创建闭包来修复此问题

for (i = 0; i < 3; i += 1) {

  console.log('inside: ', i);

  (function () {
    var j = i; 
    process.nextTick(function () {
      console.log('outside: ', j);
    });    
  })(); 

};    

console.log('end');                           
这将解决
response[key]=reply的问题

本例的第二个问题是,在异步函数完成之前会记录end。在您的代码中,这意味着在设置键+回复之前,将调用
res.json

所以,我们需要找出所有回调何时完成,然后才能记录结束。因为你知道你的列表有多大,你也知道有多少回调。这意味着我们可以在每次回调完成时进行计数。如果计数大小相等,则知道调用了所有回调

在代码中,它如下所示:

var size = 3;                               
var counter = 0;                            

var globalCallback = function () {    

  counter += 1;                             

  if (counter === size) {                   
    console.log('end');                     
  }                                         

}                                           

for (i = 0; i < size; i += 1) {             

  console.log('inside: ', i);               

  (function () {                            
    var j = i;                              
    process.nextTick(function () {          
      console.log('outside: ', j);          
      globalCallback();                     
    });                                     
  })();                                     

};  
与每次有异步函数列表时都编写这样的计数器不同,我更喜欢使用控制流库。类似async.js的东西非常流行


帮助我的是对我的代码有一个更实用的视图。您必须将其视为一个值列表,并为每个值应用一个函数。这也是async.js看起来有点像Underline.js的原因。

您是对的,这是因为checkMembership是异步的。因此,当checkMembership仍在等待答案时,for循环已完成

让我们从简化示例开始:

for (i = 0; i < 3; i += 1) {     

  console.log('inside: ', i);  

  process.nextTick(function () {  
    console.log('outside: ', i);    
  });                           

};      

console.log('end');   
因此,第一个问题是当计数器已经在2时执行回调。您可以通过创建闭包来修复此问题

for (i = 0; i < 3; i += 1) {

  console.log('inside: ', i);

  (function () {
    var j = i; 
    process.nextTick(function () {
      console.log('outside: ', j);
    });    
  })(); 

};    

console.log('end');                           
这将解决
response[key]=reply的问题

本例的第二个问题是,在异步函数完成之前会记录end。在您的代码中,这意味着在设置键+回复之前,将调用
res.json

所以,我们需要找出所有回调何时完成,然后才能记录结束。因为你知道你的列表有多大,你也知道有多少回调。这意味着我们可以在每次回调完成时进行计数。如果计数大小相等,则知道调用了所有回调

在代码中,它如下所示:

var size = 3;                               
var counter = 0;                            

var globalCallback = function () {    

  counter += 1;                             

  if (counter === size) {                   
    console.log('end');                     
  }                                         

}                                           

for (i = 0; i < size; i += 1) {             

  console.log('inside: ', i);               

  (function () {                            
    var j = i;                              
    process.nextTick(function () {          
      console.log('outside: ', j);          
      globalCallback();                     
    });                                     
  })();                                     

};  
与每次有异步函数列表时都编写这样的计数器不同,我更喜欢使用控制流库。类似async.js的东西非常流行


帮助我的是对我的代码有一个更实用的视图。您必须将其视为一个值列表,并为每个值应用一个函数。这也是async.js看起来有点像Underline.js的原因。

这肯定澄清了我从各种来源读到的内容。谢谢!所以我想我需要基本上用回调链接回调。如果有更好的条件,请原谅。我签出了async.js。。。然而,我想我还是先把异步作为一个概念,然后再深入其中。实际上,我不确定异步在幕后使用哪种技术。源代码非常好,因此您可以查看它以了解更多信息。另一个解决方案可能是承诺。它们有点争议,我不能对此发表评论,因为我从未使用过它们。这肯定澄清了我从各种来源阅读的内容。谢谢!所以我想我需要基本上用回调链接回调。如果有更好的条件,请原谅。我签出了async.js。。。然而,我想我还是先把异步作为一个概念,然后再深入其中。实际上,我不确定异步在幕后使用哪种技术。源代码非常好,因此您可以查看它以了解更多信息。另一个解决方案可能是承诺。它们有点争议,我不能对此发表评论,因为我从未使用过它们。
inside:  0
inside:  1
inside:  2
outside:  0
outside:  1
outside:  2
end