Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/407.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回调值问题_Javascript_Node.js - Fatal编程技术网

Javascript node.js回调值问题

Javascript node.js回调值问题,javascript,node.js,Javascript,Node.js,我的问题是下载具有未知扩展名的图像(可能是“png”或“jpg”或“bmp”等)。我对函数chekHead的返回值有一些问题: var fs = require('fs'), request = require('request'); var processImg = function (uri,filename){ if(checkHead(uri + 'png') > 2000){ download(uri + 'png', filename + '.p

我的问题是下载具有未知扩展名的图像(可能是“png”或“jpg”或“bmp”等)。我对函数chekHead的返回值有一些问题:

var fs = require('fs'),
    request = require('request');
var processImg = function (uri,filename){
    if(checkHead(uri + 'png') > 2000){
        download(uri + 'png', filename + '.png', function(){
            console.log(uri + 'png' + " - downloaded")
        })
    }else if(checkHead(uri + 'jpg') > 2000){
        download(uri + 'jpg', filename + '.jpg', function(){
            console.log(uri + 'jpg' + " - downloaded")
        })
    }else if(checkHead(uri + 'bmp') > 2000) {
        download(uri + 'bmp', filename + '.bmp', function () {
            console.log(uri + 'bmp' + " - downloaded")
        })
    }

}


var checkHead = function(uri){
    var length;
    request.head(uri, function(err, res, body){
        if(err) return console.log("Error");

        length = res.headers['content-length'];
        console.log(length);
    });
    return length;
}


var download = function(uri, filename, callback){
    request(uri).pipe(fs.createWriteStream('./static/' + filename).on('close', callback));
};

所以在checkHead函数中返回长度;始终返回“underfined”,但console.log返回有效数字;为什么?

NodeJS使用回调以异步方式执行代码。您的返回可能发生在回调完成之前(在本例中可能总是如此)。变量
length
位于
返回位置
未定义,因为它没有收到任何值

您可以使用承诺来链接函数,或者以另一种方式构造代码

有关承诺,请参见,例如:


您必须使用回调,以便按您所希望的方式工作:

var checkHead = function(uri,callback){
    request.head(uri, function(err, res, body){
        if(err) return console.log("Error");

        var length = res.headers['content-length'];
        console.log(length);
        callback(length);
    });
};
不幸的是,由于您的if-else逻辑,我认为目前没有办法使用承诺(jquery)来代替回调和嵌套回调,它们可能导致回调地狱,这是一种糟糕的模式,因此我对此表示抱歉:

checkHead(uri + 'png',function(length){
   if(length > 2000){
      download(uri + 'png', filename + '.png', function(){
        console.log(uri + 'png' + " - downloaded")
      });
   }
   else{  
      checkHead(uri + 'jpg',function(length){
         if(length > 2000){
            download(uri + 'jpg', filename + '.jpg', function(){
               console.log(uri + 'jpg' + " - downloaded")
            });
         }
         else{
            checkHead(uri + 'bmp',function(length){
                if(length > 2000){
                    download(uri + 'jpg', filename + '.jpg', function(){
                         console.log(uri + 'jpg' + " - downloaded")
                    });
                }
            });
         }
      });
   }

});
但是 eCamScript6解决了这个问题。这是一个关于生成器函数的好例子。主要思想是将收益率用于异步方法或函数,如request.head:

并使用“下一步”获取长度:

checkHead.next();//{value: 123, done: true}

这只是我的概念,我没有证明这一点,但生成器函数符号是这样工作的:)

Thx,明白了。但是我如何使用if/else语句来处理图像扩展(哇,非常感谢)。我想我可以用async.waterwallyes来判定这一点,这是绝对必须避免的,但ES6(EcmaScript 6)很快就会解决这个问题。不客气:)
var checkHead = function*(uri){
    var length = yield request.head(uri);
};
checkHead.next();//{value: 123, done: true}