3

我一直在努力尝试在谷歌上找到我的答案,因为我不知道我要搜索的确切术语。

如果有人要构建一个类似 msn messenger 的程序,是否有可能拥有始终打开的连接并且没有 while(true) 循环?如果是这样,有人可以指出我如何实现这一目标吗?

4

7 回答 7

4

使用boost::asio库进行套接字处理,我认为可以在数据接收时定义回调。

于 2011-07-30T16:48:34.893 回答
3

您正在寻找的一个神奇的词是异步 I/O。这可以通过使用异步 API(诸如 ReadThis() 之类的函数,它立即返回并在成功/失败时发出信号——例如但不限于 boost::asio)或通过将阻塞调用推迟到不同线程来实现。选择任何一种方法都需要仔细权衡底层实现和操作规模。

于 2011-07-30T17:32:59.993 回答
1

你想使用ACE。它有一个反应器模式,当数据可用时会通知你。

反应堆模式

于 2011-07-30T17:01:51.953 回答
1

你可以有:

 while(1) {
    sleep(100); // 100 ms
    // check if there is a message
    // process message
    //...
 }

这没关系,但是运行 10000 个线程的服务器会产生开销,因为线程会退出睡眠并检查消息,从而导致上下文切换。取而代之的是,操作系统提供类似于 Linux 的功能selectepoll允许线程等待事件。

 while(1) {
    // wait for message
    // process message
    //...
 }

使用等待,除非收到消息,否则线程不会“唤醒”。

于 2011-07-30T17:30:10.993 回答
0

您只能将 while 循环(或某种循环)隐藏在某个库中的某个地方,或者在事件回调中重新开始等待下一个 IO,但您将无法完全避免它。

于 2011-07-30T16:56:48.547 回答
0

这是一个很好的问题。就像 nj 说的,你想使用异步 I/O。太多的程序使用轮询策略。在一个系统上运行 1000 个线程并不少见。如果他们都在轮询,那么您的系统将会很慢。尽可能使用异步 I/O。

于 2011-07-30T19:05:08.183 回答
0

udp协议通信呢?您不必为每个客户端在 while 循环中等待,只需在指定端口上打开一个连接并调用接收方法

于 2011-12-29T14:06:39.737 回答