不使用while(true)循环的C#非阻塞套接字

10

我正在尝试使用C#中的非阻塞套接字进行套接字编程。 我找到了一些示例,比如这个,它似乎使用while(true)循环,但是这种方法会导致CPU占用率达到100%。 有没有一种使用事件编程风格的方式来使用非阻塞套接字? 谢谢

4个回答

9
请参考MSDN上的示例(点击此处),了解如何异步接收数据。您也可以使用Socket的BeginSend/EndSend方法来异步发送数据。
需要注意的是,回调委托在线程池线程的上下文中执行。如果在回调函数内部接收到的数据需要与另一个线程共享,例如在Windows窗体中显示数据的主UI线程,则需要使用lock关键字对数据进行同步访问。
正如您所注意到的,使用非阻塞套接字和while循环会导致处理器占用率达到100%。异步模型只会在有数据需要发送或接收时才会调用回调委托。

4

总的来说,关于阻塞/非阻塞IO,一般适用:

关键在于在现实生活中,当您的程序不进行IO操作时,它会做其他事情。这些示例都是这样人为制造出来的。

在阻塞IO中,当等待IO时,您的线程会被“阻塞”。操作系统会去做其他事情,例如允许其他线程运行。因此,通过使用多个线程,您的应用程序可以在概念上同时执行许多任务。

在非阻塞IO中,您的线程查询以查看是否可能进行IO,否则会去做其他事情。因此,您可以通过在应用程序级别显式地在它们之间切换来并行执行许多任务。


这个答案提供了一些关于为什么要进行非阻塞IO的理论,但并没有真正回答发帖者如何实现它的问题。 - squawknull

4
为了避免在重型循环中出现CPU问题,当没有数据接收时,请使用thread.sleep(100) 或更少的时间。这将让其他进程有机会执行它们的任务。

0

Socket.BeginReceive和AsyncCallback


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