eventlet和gevent之间的性能差异是什么?

20

这两个库具有相似的哲学和相似的设计决策。但是,这个流行的WSGI基准测试eventletgevent慢得多。是什么造成它们的性能差异如此之大呢?

据我所知,它们之间的主要区别在于:

  • gevent故意依赖于并与libev (libevent, 以前)耦合,而eventlet定义了独立的反应器接口,并使用selectepoll和Twisted反应器来实现特定的适配器。 额外的反应器接口会对关键性能产生影响吗?

  • gevent大部分是用Cython编写的,而eventlet是纯Python编写的。原生编译的Cython是否比纯Python更快,对于不太需要计算但需要IO绑定的程序?

  • gevent的基本元素模拟标准库的接口,而eventlet的基本元素与标准库不同,并提供附加层来模拟它。 额外的模拟层会使eventlet变慢吗?

  • eventlet.wsgi的实现只是比gevent.pywsgi差吗?

我真的很好奇,因为他们整体看起来都很相似。


我怀疑你在这里不会得到这种问题的答案。请尝试ML / Google群组。 - gwik
1
也许是这样,但这里有一个可能知道的SO用户:http://stackoverflow.com/users/197910/denis-bilenko - kkurian
2个回答

14

好的,gevent并不是“主要”使用Cython编写的,尽管有一些关键部分是使用它编写的。

Cython可以起到很大的作用。处理器优化与已编译的代码配合效果更好。例如,分支预测在基于虚拟机的系统中会崩溃,因为虚拟机执行级别上的分支间接性对其不透明。缓存足迹更紧密。编译后的代码在这里起了很大的作用,而I / O对延迟非常敏感。

同样地,libev非常快。原因也是一样的。

似乎在选择hub时,eventlet不应该使用select(Python 2.6通常默认为epoll)。但如果它被困在select上,那么它就会变得非常慢(因为python必须将select fd_set来回转换为Python列表,所以当它处于循环中间时,它会变得非常棘手)。

我没有进行任何性能分析,但我愿意打赌libev / libevent加上Cython才是主要的区别。值得注意的是,一些线程原语在gevent中是使用Cython编写的。这非常重要,因为许多代码通过IO间接触碰它们,甚至在某些地方使用标准库。

至于eventlet的额外仿真层,似乎有很多反弹。在gevent中,代码路径似乎是构造回调并让hub调用它们。eventlet似乎在做更多hub在gevent中正在做的簿记工作。不过,我还没有对其进行性能分析。关于monkeypatching本身,它们看起来相当相似。

WSGI服务器是另一个棘手的问题。值得注意的是,在gevent中,标题解析被推迟到标准库中,而在eventlet中则是他们自己实现的。我不确定这是否会产生重大影响,但如果有什么潜藏在里面也不会令人惊讶。最明显的是eventlet的服务器基于monkeypatched版本的标准库BaseHTTPServer。我无法想象这非常优化。Gevent实现了一个知道仿真的服务器。


1

对不起,回复晚了。

这个基准测试中有两个主要原因导致性能差异很大:

  • 如之前所述,gevent的关键路径已经被大力优化。
  • 该基准测试进行了压力测试。它不再是受IO限制的,因为它试图让机器运行尽可能多的请求。这就是Cython代码表现出色的地方。

在“现实世界”中,这只会在“slashdot”流量激增时发生。这很重要,应该做好准备,但当它发生时,您可以通过添加更多服务器或禁用资源密集型功能来进行反应。我还没有看到过一个基准测试在负载增加时实际上会添加更多服务器。

如果另一方面,基准测试模拟了“正常日”的负载(这会因网站而异),但通常可以近似为请求,随机暂停,重复。暂停时间越短 - 我们模拟的流量就越多。此外,基准测试的客户端还需要模拟延迟。在Linux上,可以使用神奇的netem[1]来完成,否则,可以在recv/send调用之前放置小的延迟(这将非常困难,因为基准测试通常使用更高级别的库)。

现在如果这些条件得到满足,我们实际上会对IO绑定问题进行基准测试。但结果不会太棒:所有候选者都成功地处理了10、50甚至200个qps的负载。无聊,对吧?因此,我们可以测量延迟分布、服务99%请求的时间等。Gevent仍然会展示更好的结果。但差异将很难令人印象深刻。
[1] 模拟Linux上的延迟和丢包

任何基准测试的目的都是展示极限。仅仅将“正常负载”(无论这意味着什么)放在被测对象上只能显示它是否能够在该负载下执行。如果这就是你所需要的,那么没问题,但这并不是一个基准测试。 - Alex K
@AlexK 我认为你错过了这部分内容:“因此,我们可以测量延迟分布、服务99%请求的时间等。”顺便说一下,服务N%请求的时间比最大rps更有用。 - temoto
3
我明白了。我的意思是,无论你试图衡量什么,只要你没有将其推到极限,就不能称之为基准测试。这就是我的观点。 - Alex K

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接