How to save and restore a std :: istringstream buffer?
I use a istringstream
to read a string
word by word. However, when my condition fails, I need to return istringstream
before the previous word is read. My example code works, but I want to know if there is a more direct way to use threads to accomplish this.
std::string str("my string");
std::istringstream iss(str);
std::ostringstream ossBackup << iss.rdbuf(); // Writes contents of buffer and in the process changes the buffer
std::string strBackup(ossBackup.str()); // Buffer has been saved as string
iss.str(strBackup); // Use string to restore iss buffer
iss.clear(); // Clear error states
iss >> word; // Now that I have a backup read the 1st word ("my" was read)
// Revert the `istringstream` to before the previous word was read.
iss.str(strBackup); // Restore iss to before last word was read
iss.clear(); // Clear error states
iss >> word; // "my" was read again
+3
source to share
2 answers
You can use tellg()
and seekg()
to preserve and restore their position, if you want:
#include <string>
#include <sstream>
int main()
{
std::istringstream iss("some text");
std::string word;
// save the position
std::streampos pos = iss.tellg();
// read a word
if(iss >> word)
std::cout << word << '\n';
iss.clear(); // clear eof or other errors
iss.seekg(pos); // move to saved position
while(iss >> word)
std::cout << word << '\n';
}
+3
source to share
This is indeed guaranteed to work with stringstream, but you can re-call unget()
until you reach a space character:
#include <iostream>
#include <sstream>
template <int n>
std::istream& back(std::istream& is)
{
bool state = is.good();
auto& f = std::use_facet<std::ctype<char>>(is.getloc());
for (int i = 0; i < n && is; ++i)
while (is.unget() && !f.is(f.space, is.peek()));
if (state && !is)
is.clear();
return is;
}
int main()
{
std::stringstream iss("hello world");
std::string str;
std::cout << "Value Before: ";
iss >> str;
std::cout << str << std::endl;
iss >> back<1>; // go back one word
std::cout << "Value after: ";
iss >> str;
std::cout << str;
}
+1
source to share