如何编写Node.js的asynchronous函数

我试图研究如何编写asynchronous函数。 经过大量的文件翻耕之后,对我来说还是不清楚的。

如何编写Node的asynchronous函数? 我应该如何正确实现错误事件处理?

另一个问我问题的方法是:我该如何解释下面的函数?

var async_function = function(val, callback){ process.nextTick(function(){ callback(val); }); }; 

另外,我在SO上发现了这个问题 (“如何在node.js中创build一个非阻塞asynchronous函数?”)。 我不觉得它已经被回答了。

你似乎混淆了asynchronousIO与asynchronousfunction。 node.js使用asynchronous非阻塞IO,因为非阻塞IO更好。 了解它的最好方法是去看ryan dahl的一些video。

如何编写Node的asynchronous函数?

只需编写正常的函数,唯一的区别是它们不是立即执行,而是作为callback传递。

我应该如何正确地实现错误事件处理

通常API会给你一个callback,第一个参数是err。 例如

 database.query('something', function(err, result) { if (err) handle(err); doSomething(result); }); 

是一种常见的模式。

另一种常见模式是on('error') 。 例如

 process.on('uncaughtException', function (err) { console.log('Caught exception: ' + err); }); 

编辑:

 var async_function = function(val, callback){ process.nextTick(function(){ callback(val); }); }; 

上面的函数叫做

 async_function(42, function(val) { console.log(val) }); console.log(43); 

将以asynchronous方式打印42到控制台。 特别是process.nextTick在当前的eventloop调用堆栈为空之后触发。 在async_functionconsole.log(43)已经运行之后,该调用堆栈是空的。 所以我们打印43,然后是42。

你应该在事件循环上做一些阅读。

你应该看这个: Node Tuts第19集 – asynchronous迭代模式

它应该回答你的问题。

仅通过callback是不够的。 例如,你必须使用settimer来使函数asynchronous。

示例:不是asynchronous函数:

 function a() { var a = 0; for(i=0; i<10000000; i++) { a++; }; b(); }; function b() { var a = 0; for(i=0; i<10000000; i++) { a++; }; c(); }; function c() { for(i=0; i<10000000; i++) { }; console.log("async finished!"); }; a(); console.log("This should be good"); 

如果你将运行上面的例子,这应该是好的,将不得不等待,直到那些function将完成工作。

伪multithreading(asynchronous)function:

 function a() { setTimeout ( function() { var a = 0; for(i=0; i<10000000; i++) { a++; }; b(); }, 0); }; function b() { setTimeout ( function() { var a = 0; for(i=0; i<10000000; i++) { a++; }; c(); }, 0); }; function c() { setTimeout ( function() { for(i=0; i<10000000; i++) { }; console.log("async finished!"); }, 0); }; a(); console.log("This should be good"); 

这将是一个真正的asynchronous。 这应该是好的将在asynchronous完成之前写入。

试试这个,它适用于节点和浏览器。

 isNode = (typeof exports !== 'undefined') && (typeof module !== 'undefined') && (typeof module.exports !== 'undefined') && (typeof navigator === 'undefined' || typeof navigator.appName === 'undefined') ? true : false, asyncIt = (isNode ? function (func) { process.nextTick(function () { func(); }); } : function (func) { setTimeout(func, 5); });