Public Group

Skipping Delimiters in Input

This topic is 4409 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

Recommended Posts

This seems like a pretty simple question, but I'm having a whole lot of trouble skipping certain characters (delimiters) when reading data from a file in C++. For example, lets say I have a list of names that are seperated by commas. How can I "ignore" the comma and just read in the names? The file may look something like this:
Doe, John
Doe, Jane
Smith, Bob
Miller, Jay
Intuition has led me to the ignore() method, but that doesn't seem to work in this situation as it totally ignores everything up to a certain number of characters or a delimiter. I've tried using the get() method with a char* buffer to read into, but then I get strange results using the >> operator; eof() is NEVER false and I read in garbage. How could I approach this for some delimiter I want to throw away? I'm guessing the same solution would also work in binary mode, no? Thanks!

Share on other sites
Whoops. It seems like get() will work; I forgot to take into account where the get pointer would be after calling get() (I assumed it would move over white space just as using >> does :-P ).

Any input is still welcome.

Share on other sites
Quote:
 Original post by GenuineXPAny input is still welcome.
You might check out boost::tokenizer. It's designed for simple parsing (as in your example) and is very easy to use.

Share on other sites
You could use the string object
string str = "Snorre, Sturlason";string::size_type pos = str.find_first_of(", ");cout << "First name: " << str.substr(0, pos) << endl;cout << "Last name: " << str.substr(pos + 2) << endl;

but I suspect there might be more suitable formatting methods as well

[Edited by - pulpfist on November 16, 2006 7:59:43 PM]

Share on other sites
Here's a simple split function that seems to fit your request. It also disposes of all characters matching pDelim (may either be char or string). I wrote this last night so beware of any bugs. [smile]

typedef std::vector<std::string> t_strings;template<typename T>const t_strings& split(const std::string& pStr, const T& pDelim){    static t_strings buf;    buf.clear();    size_t _first = 0;    size_t _last = 0;    while (_first != std::string::npos)    {        _first = pStr.find_first_not_of(pDelim, _last);        if (_first == std::string::npos) break;        _last = pStr.find_first_of(pDelim, _first);        buf.push_back(pStr.substr(_first, _last-_first));    }    return buf;}

Share on other sites
std::getline takes an optional third argument specifying the "line separator". You can read comma-separated items, therefore, by std::getline(the_stream, the_string, ','); . You would get the "last name" that way and the "first name" by reading the rest of the line normally (with the 2-arg std::getline).

That will leave leading and trailing whitespace, of course. You could get rid of the leading whitespace right away by reading into std::ws, but you can't deal with trailing whitespace directly with a stream (the stream would have to be psychic: if it sees a long run of spaces, who knows whether the next character after the spaces is the separator, or some other character?). Therefore, I suggest making a utility function to "trim" std::strings, front and back. Have it accept the list of whitespace characters as a const char*, defaulting to " \t", and use substring operations to skip leading and trailing characters that are in the whitespace specification. (Hint: Don't search manually; use the string member functions find_first_not_of and find_last_not_of.)

1. 1
2. 2
3. 3
Rutin
15
4. 4
5. 5

• 10
• 9
• 9
• 11
• 11
• Forum Statistics

• Total Topics
633685
• Total Posts
3013317
×