我想在C#中创建一个高性能的服务器,可能需要约10万个客户端。现在我开始用C#编写TcpServer,并为每个客户端连接打开一个新线程。我还使用一个线程来接受连接。到目前为止一切顺利,工作正常。
服务器必须反序列化AMF传入对象做一些逻辑(比如保存播放器的位置)并发回一些对象(序列化对象)。我并不担心序列化/反序列化部分atm。
我主要担心的是,我将拥有10k个客户端的大量线程,并且我已经阅读过某个操作系统只能保持几个线程的线程。
有没有关于编写体面的异步线程服务器的资料/文章?还有其他可能性还是10k线程可以正常工作?我看过谷歌,但我找不到很多关于设计模式的信息或解释清楚的方法
答案 0 :(得分:4)
你会遇到很多问题。
由于几个原因,您无法启动10,000个线程。它会破坏内核调度程序。如果您运行的是32位,则默认堆栈地址空间为1MB意味着10k线程将保留大约10GB的地址空间。那会失败。
您也不能使用简单的选择系统。在它的核心,选择是O(N)的插座数量。使用10k插座,这很糟糕。
您可以使用IO完成端口。这是他们设计的场景。据我所知,没有稳定的托管IO完成端口库。您必须使用P / Invoke或Managed C ++编写自己的代码。玩得开心。
答案 1 :(得分:3)
编写高效的多线程服务器的方法是使用I / O完成端口(每个请求使用一个线程是非常低效的,如@Marcelo所提到的)。
如果您使用.NET套接字类的异步版本,则可以免费获得。请参阅this question,其中包含指向文档的内容。
答案 2 :(得分:1)
您绝对不希望每个请求都有一个帖子。即使您拥有较少的客户端,创建和销毁线程的开销也会削弱服务器,并且您无法获得10,000个线程;操作系统调度程序很久就会死于可怕的死亡。
网上有很多关于C#中异步服务器编程的文章(例如,here)。只是谷歌一点。
答案 3 :(得分:1)
您希望了解使用IO completion ports。你基本上有一个线程池和一个IO操作队列。
I / O完成端口提供 高效的线程模型 处理多个异步I / O. 多处理器系统上的请求。 当进程创建I / O时 完成端口,系统创建一个 请求的关联队列对象 其唯一目的是为这些服务 要求。处理许多的进程 并发异步I / O请求 可以更快,更有效地做到这一点 通过使用I / O完成端口 与预先分配的结合 线程池比通过创建线程 在他们收到I / O时 请求。