Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why doesn't the istreambuf_iterator advance work

I was reading Constructing a vector with istream_iterators which is about reading a complete file contents into a vector of chars. While I want a portion of a file to be loaded in to a vector of chars.

#include <iostream>
#include <fstream>
#include <iterator>
#include <vector>
#include <algorithm>

using namespace std;

int main(int argc, char *argv[])
{
    ifstream ifs(argv[1], ios::binary);
    istreambuf_iterator<char> beginItr(ifs);
    istreambuf_iterator<char> endItr(beginItr);
    advance(endItr, 4);
    vector<char> data(beginItr, endItr);
    for_each(data.cbegin(), data.cend(), [](char ch)
    {
            cout << ch << endl;
    });
}

This doesn't work, since advance doesn't work, while the aforementioned question's accepted answer works. Why doesn't the advance work on istreambuf_iterator?

Also

  endItr++;
  endItr++;
  endItr++;
  endItr++;
  cout << distance(beginItr, endItr) << endl;

returns a 0. Please somebody explain what is going on!

like image 655
legends2k Avatar asked Dec 18 '25 10:12

legends2k


2 Answers

Why doesn't the advance work on istreambuf_iterator?

It works. It advances the iterator. The problem is that an istreambuf_iterator is an input iterator but not a forward iterator, meaning it is a single pass iterator: once you advance it, you can never access the previous state again. To do what you want you can simply use an old-fashioned for loop that counts to 4.

like image 66
R. Martinho Fernandes Avatar answered Dec 21 '25 02:12

R. Martinho Fernandes


istreambuf_iterator reads successive bytes from a basic_streambuf. It does not support positioning (basic_istream::seekg and basic_istream::tellg).

This is because it is a single-pass input iterator, not a forward iterator or a random-access iterator; it is designed to be able to work with streams that do not support positioning (e.g. pipes or TCP sockets).

You may find some of the solutions in bidirectional iterator over file/ifstream useful.

like image 39
ecatmur Avatar answered Dec 21 '25 04:12

ecatmur



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!