为什么Q延迟在Node.js上如此之慢?

Wil*_*der 10 node.js promise deferred q

所以我在Node.js中创建了这个简单的测试服务器.
每当我做直接响应时,我得到2200个请求/秒(快!).当我只包裹一个简单的Q延迟它时,它下降到580个请求/秒(慢4倍!).任何人都能解释这个巨大的差异吗?

// Requires
var server = require('http');
var q = require('q');

// Start server
var http = require('http');
http.createServer(function(request, response) {

    // Comment out either of two below sections

// Without deferred
// 2200 reqs/second
response.writeHead(200, {"Content-Type": "text/html"});
response.write("test");
response.end();

// Q deferred
// 580 reqs/second
var deferred = q.defer();
deferred.promise.then(function() {
    response.writeHead(200, {"Content-Type": "text/html"});
    response.write("test");
    response.end();
});
deferred.resolve();
}).listen(1234);
Run Code Online (Sandbox Code Playgroud)

Stu*_*t K 21

编辑:自从Q 0.9.6以来,堆栈跟踪已经关闭,性能已经大大提高.(可以重新启用它们以进行调试Q.longStackSupport = true;)

原文:Q promises很慢,因为它们捕获每个承诺的完整堆栈跟踪以帮助调试.这很慢.您可以将它们关闭Q.longStackJumpLimit = 0;(这可能是下一版本中的默认设置).我们通过关闭它们发现了大约30倍的加速.你可以在这里找到更多信息https://github.com/kriskowal/q#long-stack-traces

在nextTick实现上也有一些性能工作,但我认为上面是主要原因.

  • 在Q 0.9.6中,默认情况下,长堆栈跟踪已关闭. (3认同)

Mar*_*wak 5

我所知道的原因是:

  1. Q使用Object.freeze,这会减慢V8的幅度

  2. 许多nextTick调用(已在评论中提到).然而,对于最新的Node.js版本(v0.10),这应该不是那么多,因为nextTick开销很小.

  • Q前一段时间回答了这个问题 - 它不再使用Object.freeze.我们也尽可能地展开`nextTick`.但是我们经常使用`nextTick`. (8认同)
  • 建议:使用另一个延迟的lib :) (2认同)