read part of a file with iostreams

后端 未结 3 941
忘了有多久
忘了有多久 2021-02-15 14:18

Can I open an ifstream (or set an existing one in any way) to only read part of a file? For example, I would like to have my ifstream read a file from

3条回答
  •  孤独总比滥情好
    2021-02-15 15:06

    It definetly can be done by implementing a filtering stream buffer: you would derive from std::streambuf and take the range you want to expose and the underlying stream buffer (well, a pointer to it) as arguments. Then you would seek to the start location. An overridden underflow() function would read from the underlying stream buffer into its buffer until has consumed as many characters as were desired. Here is a somewhat rough and entirely untested version:

    #include 
    struct rangebuf: std::streambuf {
        rangebuf(std::streampos start,
                        size_t size,
                        std::streambuf* sbuf):
            size_(size), sbuf_(sbuf)
        {
            sbuf->seekpos(start, std::ios_base::in);
        }
        int underflow() {
            size_t r(this->sbuf_->sgetn(this->buf_,
                std::min(sizeof(this->buf_), this->size_));
            this->size -= r;
            this->setg(this->buf_, this->buf_, this->buf_ + r);
            return this->gptr() == this->egptr()
                ? traits_type::eof()
                : traits_type::to_int_type(*this->gptr());
        }
        size_t size_;
        std::streambuf* sbuf_;
    };
    

    You can use a pointer to an instance of this stream buffer to initialuze an std::istream. If this a recurring need, you might want to create a class derived from std::istream setting up the stream buffer instead.

提交回复
热议问题