阻止从std :: ifstream读取

时间:2017-06-05 10:04:42

标签: c++ ifstream

我正在使用std::ifstream::read从管道(Linux)或类似管道的设备对象(Windows)中读取。但是,当没有更多数据时,read读取0个字节并设置EOF。有没有办法从ifstream进行阻塞读取,这样只有在有更多数据时它才会返回?

我宁愿不忙等待EOF标志清除。

如果C ++标准库无法实现,那么最接近的其他选项是什么?我可以在纯C中执行此操作,还是必须使用特定于操作系统的API?

2 个答案:

答案 0 :(得分:3)

不幸的是,std在任何非算法功能上都很差,比如IO。您始终必须依赖第三方解决方案。幸运的是,有Boost,如果你不介意的话,我会建议用它来减少OS特定的代码。

    namespace bs = boost::iostreams;
    int fd; // Create, for example, Posix file descriptor and specify necessary flags for it.
    bs::file_descriptor_source fds(fd);
    bs::stream<bs::file_descriptor_source> stream(fds);
    // Work with the stream as it is std stream

在这个小例子中,我使用Boost IO Streams,特别是file_descriptor_source作为底层流设备,并在其中隐藏Windows或Posix特定管道。您自己打开的管道,因此您可以根据需要配置管道。

答案 1 :(得分:0)

好吧似乎无法进行阻止读取。清除错误位无济于事。只有在这个例子中重新打开fifo:

int main(int argc, char **argv)
{
    int rc=0;
    enum FATAL {ERR_ARGV,ERR_OPEN_FILE};
    try
    {
            if( argv[1] == NULL) throw ERR_ARGV;
            std::ifstream fifo;

            while(1)
            {
                    fifo.open(argv[1],std::ifstream::in);
                    if( !fifo.is_open() ) throw ERR_OPEN_FILE;

                    std::string line;
                    while(std::getline(fifo,line))
                    {
                            std::cout << line << "\n"; fflush(stdout);
                    }
                    fifo.close();
            }
            // never should come here
    }
    catch(FATAL e)
    {
            rc=e;
            switch(e)
            {
            case ERR_ARGV:
                    std::cerr << "ERROR: argument 1 should be a fifo file name\n";
                    break;
            case ERR_OPEN_FILE:
                    std::cerr << "ERROR: unabel to open file " << argv[1] << "\n";
                    break;
            }
    }
    return(rc);
}

我测试了这段代码,它可以从fifo中无休止地读取。