无论您使用什么语言,300,000 个并发的活动连接都太多,无法在单个进程或单个计算机上合理支持。如果你的程序需要对数据做任何事情,你将需要更多的硬件。
让我们做一些简单的数学运算来支持这一点。
假设您的用户平均每 5 秒左右单击鼠标或点击一个键或以其他方式执行一次操作。这是每秒 60,000 个读取事件。现在,假设每场比赛有 5 个玩家,这意味着每秒额外的 300,000 个写入事件,假设您必须为每个事件更新所有玩家。所以:每秒要计算 360,000 位“事物”——假设您只需要计算一些字节用于输入和输出,并且您没有任何计算密集型游戏逻辑(如 AI 玩家)可以调用。
假设您正在使用M3 Double Extra Large实例,这是亚马逊目前提供的最大实例。那是8个虚拟核心。假设您的程序是完全可并行化的,这意味着您的游戏中的每一个输入或输出事件(包括所有数据库活动、外部 Web 服务 API 调用等)都需要在 0.00002 秒内处理。现在,这让您完全没有开销来处理负载峰值,因此您真的希望将其减半,以便在流量变化的情况下保持合理的希望,这意味着每个事件 0.00001 秒。这是十微秒的硬限制让您的所有游戏代码执行;大多数情况下,这种响应能力是以毫秒为单位来衡量的。time.time()
在我的(相当快的)台式计算机上,如果中间没有其他代码,从一个调用到下一个调用几乎需要两微秒。即使是经过微调的 C 代码也无法在一微秒内完成大量有用的工作。
这意味着,如果你想达到这种规模,你真的,真的需要能够一次在多台服务器上运行你的服务。而且,一旦您的服务可以在两台服务器上运行,通常放在三台、五台或一百台服务器上也没什么大不了的。
虽然我非常想告诉你使用 Twisted(你应该有很多很好的理由),但真正的结论是你可以使用任何你喜欢的东西并且它将很好地“扩展到”您的数十万个连接,前提是您编写它的方式不依赖于为您的所有请求提供服务的单个服务器。在您有一个服务实际处理 300k 实时并发连接时,使用 gevent 或 Twisted 或 Tornado 或 Eventlet 或 EventMachine 之间的性能差异——如果实际上有任何差异——将是之间的差异,比如说,从亚马逊租用 50 和 55 个实例。(而且,很难说哪一个会更快,因为这在某种程度上取决于你会用它做什么。)然而,分析你自己的代码和在开发它时密切关注它的性能之间的区别在于租赁 500 台机器和租赁 50 台机器的区别。