大神们看看这段代码,最后的注释里有我的疑问。



 var fs = require('fs');

var helper = function(fn) {
        return function() {
                var args = [].slice.call(arguments);
                var pass;
                args.push(function() {
                        if (pass) {
                                pass.apply(null, arguments);
                        }
                });

                fn.apply(null, args);

                return function(fn) {
                        pass = fn;
                }
        }
}

var readFile = helper(fs.readFile);

var flow = function*() {
        var txt = yield readFile('a.txt', 'utf8');
        console.log('txt : ', txt);
}

var g = flow();
var ret = g.next();
ret.value(function(err, data) {
        if (err) {
                throw err;
        } else {
                g.next(data);
                //这里返回txt的值,但是ret.value里的回调函数怎么保证及时传到readFile()里面的,fn.apply()执行时callback是function(pass){if(pass){}},而pass的值是在后面的ret.value()执行时才传递的?
        }
});

es6 JavaScript

野良熊kuma 9 years, 2 months ago

1)


 readFile('a.txt', 'utf8')

返回一个函数,这个函数接收一个函数为输入参数


 var flow = function*() {
        var txt = yield readFile('a.txt', 'utf8');
        console.log('txt : ', txt);
}

flow是一个generator函数(function* 还带有yield),所以


 g.next();

函数执行后返回一个函数,也就是ret.value是一个函数


 ret.value(function *readFileCallBack*(err, data) {});

执行后就相当helper的闭包函数中的pass参数得到了一个 readFileCallBack 这个函数

2) fs.readFile请求调用后,会在下一次的时间循环中,会检查指定的文件是否有内容被读到,如果读取到或读取失败就会调用指定的回调。
也就是文件读取到内容后的回调的执行和当前代码不是在同一个时间序列中


 args.push(function() {
                        if (pass) {
                                pass.apply(null, arguments);
                        }
                });

以上代码以及为fs.readFile添加了一个回调,如果pass不为空,pass函数会再调用apply方法,将传给回调函数的err,data参数传入pass

3)


 g.next(data);

恢复generator函数的执行
就是执行


 var txt=data;
console.log('txt : ', txt);

茶茶丸泡的茶 answered 9 years, 2 months ago

Your Answer