Search code examples
c++stringspacesistream

Reading constant number of characters in C++


How would you read a string if it was no longer than 20 characters and could contain spaces in C++? For example I have this kind of file:

3
Namama               4 5 12
Cool                 4 2 34
Not So Cool          4 2 45

I want to write it in the most basic way possible. And I would prefer using only C++ (no C thingies) in this case. This means I want to store it in std::string.

I could use istream::get or istream::getline but then I have to avoid the new line characters. This is problematic (and the code I'm writing is going to be shown to beginners).

What are your solutions for this problem?

Edit:

As asked I'm going to tell you what I have tried but I don't think it's going to be any good. I am not a C++ beginner and usually I would have used something like istream::get and char array but removing new line characters might seem too techy for some people.

So... Either reading char array or std::string using istream::operator>> fails because it stops reading when they see space character (and I may have to read several words). This means the following code fails:

char name[21];
std::cin >> name;

or...

std::string name;
std::cin >> name;

Another thing is that new line characters differ from system to system and actually Windows use two of them by default and I have tried using istream::ignore with 2 as an argument on Windows and that was the only way to ignore the new line and I came to conclusion that it's because Windows use two characters for a new line mark. That means it wouldn't work on Linux and it would have to be more complex... Again - bad for beginners.


Solution

  • If you want to read exactly 20 characters,

    for(int i=0; i<3; ++i) {
        std::string result;
        int one, two, three;
    
        result.resize(20);
        if (!std::cin.read(&result[0], 20)) throw std::runtime_error("reading buffer failed!");
    
        if (!std::cin >> one >> two >> three) throw std::runtime_error("reading numbers failed!");
        if (!std::cin.ignore(1000, '\n')) throw std::runtime_error("ignore failed!");
    }
    

    If you don't want exactly 20 characters, how do you know when you've reached the end of the string?