【问题标题】:Why FD_SET/FD_ZERO for select() inside of loop?为什么 FD_SET/FD_ZERO for select() 在循环内?
【发布时间】:2011-11-30 01:36:49
【问题描述】:

我正在使用 select 函数在我的套接字之间进行通信。我有一个 while 循环,我有 -

    while(!done) {

    FD_ZERO(&read_flags);
    FD_ZERO(&write_flags);
    FD_SET(comm_fd1, &read_flags);
    FD_SET(comm_fd2, &read_flags);
    FD_SET(STDIN_FILENO, &read_flags);
    FD_SET(comm_fd1, &write_flags);
    FD_SET(comm_fd2, &write_flags);
    FD_SET(STDIN_FILENO, &write_flags);

    //call select
    sel = select(comm_fd1+comm_fd2+1, &read_flags, &write_flags, (fd_set*)0, &waitd);

在客户端使用不同的变量也是如此。我从在线教程中获得了这种基本技术,然后就开始使用它。然后它击中了我 - 为什么我每次循环时都要清除集合并添加文件描述符?如果它们已经添加,为什么要清除它们并再次添加?所以我在此之前只尝试过一次,并且代码不再起作用了。有人可以解释为什么吗?仅仅是因为select修改了集合的内容吗?感谢您提供任何帮助和/或见解。

【问题讨论】:

    标签: c++ select tcp file-descriptor


    【解决方案1】:

    select 返回时,它已更新集合以显示哪些文件描述符已准备好进行读/写/异常。所有其他标志已被清除。

    重新启用在开始另一个选择之前清除的文件描述符很重要,否则,您将不再等待这些文件描述符。

    至于重新清除,这可能是一个好习惯,因为如果您需要更改文件描述符集(例如将新打开的套接字添加到读取集),您需要清除并且每次都重新构建它,以便随着程序状态的变化它是正确的。

    【讨论】:

    • 另请注意,每次循环时都应重置 timeval 结构(在您的示例中为等待)。
    【解决方案2】:

    仅仅是因为select修改了集合的内容吗?

    是的,select 返回后,集合中只剩下准备好的描述符。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-10-01
      • 1970-01-01
      • 1970-01-01
      • 2016-08-31
      • 2017-09-20
      • 1970-01-01
      • 2019-08-20
      • 1970-01-01
      相关资源
      最近更新 更多